Ignore ABS symbols in ObjSymbols::for_range
- Add ObjSymbols::iter_ordered for all symbols (including ABS) - Extract duplicated logic into ObjSymbols::for_relocation
This commit is contained in:
parent
8f461b8e0a
commit
f06a6ffbdd
|
@ -519,67 +519,9 @@ impl Tracker {
|
||||||
Some(v) => v,
|
Some(v) => v,
|
||||||
None => continue,
|
None => continue,
|
||||||
};
|
};
|
||||||
// Try to find a previous sized symbol that encompasses the target
|
if let Some((symbol_idx, symbol)) =
|
||||||
let target_symbol = {
|
obj.symbols.for_relocation(target, reloc_kind)?
|
||||||
let mut result = None;
|
{
|
||||||
for (_addr, symbol_idxs) in obj.symbols.indexes_for_range(..=target).rev() {
|
|
||||||
let symbol_idx = if symbol_idxs.len() == 1 {
|
|
||||||
symbol_idxs.first().cloned().unwrap()
|
|
||||||
} else {
|
|
||||||
let mut symbol_idxs = symbol_idxs.to_vec();
|
|
||||||
symbol_idxs.sort_by_key(|&symbol_idx| {
|
|
||||||
let symbol = obj.symbols.at(symbol_idx);
|
|
||||||
let mut rank = match symbol.kind {
|
|
||||||
ObjSymbolKind::Function | ObjSymbolKind::Object => {
|
|
||||||
match reloc_kind {
|
|
||||||
ObjRelocKind::PpcAddr16Hi
|
|
||||||
| ObjRelocKind::PpcAddr16Ha
|
|
||||||
| ObjRelocKind::PpcAddr16Lo => 1,
|
|
||||||
ObjRelocKind::Absolute
|
|
||||||
| ObjRelocKind::PpcRel24
|
|
||||||
| ObjRelocKind::PpcRel14
|
|
||||||
| ObjRelocKind::PpcEmbSda21 => 2,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// Label
|
|
||||||
ObjSymbolKind::Unknown => match reloc_kind {
|
|
||||||
ObjRelocKind::PpcAddr16Hi
|
|
||||||
| ObjRelocKind::PpcAddr16Ha
|
|
||||||
| ObjRelocKind::PpcAddr16Lo
|
|
||||||
if !symbol.name.starts_with("..") =>
|
|
||||||
{
|
|
||||||
3
|
|
||||||
}
|
|
||||||
_ => 1,
|
|
||||||
},
|
|
||||||
ObjSymbolKind::Section => -1,
|
|
||||||
};
|
|
||||||
if symbol.size > 0 {
|
|
||||||
rank += 1;
|
|
||||||
}
|
|
||||||
-rank
|
|
||||||
});
|
|
||||||
match symbol_idxs.first().cloned() {
|
|
||||||
Some(v) => v,
|
|
||||||
None => continue,
|
|
||||||
}
|
|
||||||
};
|
|
||||||
let symbol = obj.symbols.at(symbol_idx);
|
|
||||||
if symbol.address == target as u64 {
|
|
||||||
result = Some(symbol_idx);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if symbol.size > 0 {
|
|
||||||
if symbol.address + symbol.size > target as u64 {
|
|
||||||
result = Some(symbol_idx);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
result
|
|
||||||
};
|
|
||||||
if let Some(symbol_idx) = target_symbol {
|
|
||||||
let symbol = obj.symbols.at(symbol_idx);
|
|
||||||
let symbol_address = symbol.address;
|
let symbol_address = symbol.address;
|
||||||
// TODO meh
|
// TODO meh
|
||||||
if data_kind != ObjDataKind::Unknown
|
if data_kind != ObjDataKind::Unknown
|
||||||
|
|
|
@ -109,7 +109,7 @@ fn info(args: InfoArgs) -> Result<()> {
|
||||||
}
|
}
|
||||||
println!("\nDiscovered symbols:");
|
println!("\nDiscovered symbols:");
|
||||||
println!("\t{: >23} | {: <10} | {: <10}", "Name", "Address", "Size");
|
println!("\t{: >23} | {: <10} | {: <10}", "Name", "Address", "Size");
|
||||||
for (_, symbol) in obj.symbols.for_range(..) {
|
for (_, symbol) in obj.symbols.iter_ordered() {
|
||||||
if symbol.name.starts_with('@') || symbol.name.starts_with("fn_") {
|
if symbol.name.starts_with('@') || symbol.name.starts_with("fn_") {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
|
@ -161,67 +161,9 @@ fn merge(args: MergeArgs) -> Result<()> {
|
||||||
let source_section_index = obj.section_at(source_addr)?.index;
|
let source_section_index = obj.section_at(source_addr)?.index;
|
||||||
let target_section_index = obj.section_at(target_addr)?.index;
|
let target_section_index = obj.section_at(target_addr)?.index;
|
||||||
|
|
||||||
// Try to find a previous sized symbol that encompasses the target
|
let (symbol_idx, addend) = if let Some((symbol_idx, symbol)) =
|
||||||
let target_symbol = {
|
obj.symbols.for_relocation(target_addr, rel_reloc.kind)?
|
||||||
let mut result = None;
|
{
|
||||||
for (_addr, symbol_idxs) in obj.symbols.indexes_for_range(..=target_addr).rev() {
|
|
||||||
let symbol_idx = if symbol_idxs.len() == 1 {
|
|
||||||
symbol_idxs.first().cloned().unwrap()
|
|
||||||
} else {
|
|
||||||
let mut symbol_idxs = symbol_idxs.to_vec();
|
|
||||||
symbol_idxs.sort_by_key(|&symbol_idx| {
|
|
||||||
let symbol = obj.symbols.at(symbol_idx);
|
|
||||||
let mut rank = match symbol.kind {
|
|
||||||
ObjSymbolKind::Function | ObjSymbolKind::Object => {
|
|
||||||
match rel_reloc.kind {
|
|
||||||
ObjRelocKind::PpcAddr16Hi
|
|
||||||
| ObjRelocKind::PpcAddr16Ha
|
|
||||||
| ObjRelocKind::PpcAddr16Lo => 1,
|
|
||||||
ObjRelocKind::Absolute
|
|
||||||
| ObjRelocKind::PpcRel24
|
|
||||||
| ObjRelocKind::PpcRel14
|
|
||||||
| ObjRelocKind::PpcEmbSda21 => 2,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// Label
|
|
||||||
ObjSymbolKind::Unknown => match rel_reloc.kind {
|
|
||||||
ObjRelocKind::PpcAddr16Hi
|
|
||||||
| ObjRelocKind::PpcAddr16Ha
|
|
||||||
| ObjRelocKind::PpcAddr16Lo
|
|
||||||
if !symbol.name.starts_with("..") =>
|
|
||||||
{
|
|
||||||
3
|
|
||||||
}
|
|
||||||
_ => 1,
|
|
||||||
},
|
|
||||||
ObjSymbolKind::Section => -1,
|
|
||||||
};
|
|
||||||
if symbol.size > 0 {
|
|
||||||
rank += 1;
|
|
||||||
}
|
|
||||||
-rank
|
|
||||||
});
|
|
||||||
match symbol_idxs.first().cloned() {
|
|
||||||
Some(v) => v,
|
|
||||||
None => continue,
|
|
||||||
}
|
|
||||||
};
|
|
||||||
let symbol = obj.symbols.at(symbol_idx);
|
|
||||||
if symbol.address == target_addr as u64 {
|
|
||||||
result = Some(symbol_idx);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if symbol.size > 0 {
|
|
||||||
if symbol.address + symbol.size > target_addr as u64 {
|
|
||||||
result = Some(symbol_idx);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
result
|
|
||||||
};
|
|
||||||
let (symbol_idx, addend) = if let Some(symbol_idx) = target_symbol {
|
|
||||||
let symbol = obj.symbols.at(symbol_idx);
|
|
||||||
(symbol_idx, target_addr as i64 - symbol.address as i64)
|
(symbol_idx, target_addr as i64 - symbol.address as i64)
|
||||||
} else {
|
} else {
|
||||||
// Create a new label
|
// Create a new label
|
||||||
|
|
|
@ -341,6 +341,14 @@ impl ObjSymbols {
|
||||||
Ok(result)
|
Ok(result)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Iterate over all in address ascending order, including ABS symbols
|
||||||
|
pub fn iter_ordered(&self) -> impl DoubleEndedIterator<Item = (SymbolIndex, &ObjSymbol)> {
|
||||||
|
self.symbols_by_address
|
||||||
|
.iter()
|
||||||
|
.flat_map(move |(_, v)| v.iter().map(move |u| (*u, &self.symbols[*u])))
|
||||||
|
}
|
||||||
|
|
||||||
|
// Iterate over range in address ascending order, excluding ABS symbols
|
||||||
pub fn for_range<R>(
|
pub fn for_range<R>(
|
||||||
&self,
|
&self,
|
||||||
range: R,
|
range: R,
|
||||||
|
@ -351,6 +359,8 @@ impl ObjSymbols {
|
||||||
self.symbols_by_address
|
self.symbols_by_address
|
||||||
.range(range)
|
.range(range)
|
||||||
.flat_map(move |(_, v)| v.iter().map(move |u| (*u, &self.symbols[*u])))
|
.flat_map(move |(_, v)| v.iter().map(move |u| (*u, &self.symbols[*u])))
|
||||||
|
// Ignore ABS symbols
|
||||||
|
.filter(move |(_, sym)| sym.section.is_some())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn indexes_for_range<R>(
|
pub fn indexes_for_range<R>(
|
||||||
|
@ -421,6 +431,68 @@ impl ObjSymbols {
|
||||||
*symbol_ref = symbol;
|
*symbol_ref = symbol;
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Try to find a previous sized symbol that encompasses the target
|
||||||
|
pub fn for_relocation(
|
||||||
|
&self,
|
||||||
|
target_addr: u32,
|
||||||
|
reloc_kind: ObjRelocKind,
|
||||||
|
) -> Result<Option<(SymbolIndex, &ObjSymbol)>> {
|
||||||
|
let mut result = None;
|
||||||
|
for (_addr, symbol_idxs) in self.indexes_for_range(..=target_addr).rev() {
|
||||||
|
let symbol_idx = if symbol_idxs.len() == 1 {
|
||||||
|
symbol_idxs.first().cloned().unwrap()
|
||||||
|
} else {
|
||||||
|
let mut symbol_idxs = symbol_idxs.to_vec();
|
||||||
|
symbol_idxs.sort_by_key(|&symbol_idx| {
|
||||||
|
let symbol = self.at(symbol_idx);
|
||||||
|
let mut rank = match symbol.kind {
|
||||||
|
ObjSymbolKind::Function | ObjSymbolKind::Object => match reloc_kind {
|
||||||
|
ObjRelocKind::PpcAddr16Hi
|
||||||
|
| ObjRelocKind::PpcAddr16Ha
|
||||||
|
| ObjRelocKind::PpcAddr16Lo => 1,
|
||||||
|
ObjRelocKind::Absolute
|
||||||
|
| ObjRelocKind::PpcRel24
|
||||||
|
| ObjRelocKind::PpcRel14
|
||||||
|
| ObjRelocKind::PpcEmbSda21 => 2,
|
||||||
|
},
|
||||||
|
// Label
|
||||||
|
ObjSymbolKind::Unknown => match reloc_kind {
|
||||||
|
ObjRelocKind::PpcAddr16Hi
|
||||||
|
| ObjRelocKind::PpcAddr16Ha
|
||||||
|
| ObjRelocKind::PpcAddr16Lo
|
||||||
|
if !symbol.name.starts_with("..") =>
|
||||||
|
{
|
||||||
|
3
|
||||||
|
}
|
||||||
|
_ => 1,
|
||||||
|
},
|
||||||
|
ObjSymbolKind::Section => -1,
|
||||||
|
};
|
||||||
|
if symbol.size > 0 {
|
||||||
|
rank += 1;
|
||||||
|
}
|
||||||
|
-rank
|
||||||
|
});
|
||||||
|
match symbol_idxs.first().cloned() {
|
||||||
|
Some(v) => v,
|
||||||
|
None => continue,
|
||||||
|
}
|
||||||
|
};
|
||||||
|
let symbol = self.at(symbol_idx);
|
||||||
|
if symbol.address == target_addr as u64 {
|
||||||
|
result = Some((symbol_idx, symbol));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if symbol.size > 0 {
|
||||||
|
if symbol.address + symbol.size > target_addr as u64 {
|
||||||
|
result = Some((symbol_idx, symbol));
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Ok(result)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ObjInfo {
|
impl ObjInfo {
|
||||||
|
|
|
@ -106,7 +106,7 @@ fn is_skip_symbol(symbol: &ObjSymbol) -> bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn write_symbols<W: Write>(w: &mut W, obj: &ObjInfo) -> Result<()> {
|
pub fn write_symbols<W: Write>(w: &mut W, obj: &ObjInfo) -> Result<()> {
|
||||||
for (_, symbol) in obj.symbols.for_range(..) {
|
for (_, symbol) in obj.symbols.iter_ordered() {
|
||||||
if symbol.kind == ObjSymbolKind::Section
|
if symbol.kind == ObjSymbolKind::Section
|
||||||
// Ignore absolute symbols for now (usually linker-generated)
|
// Ignore absolute symbols for now (usually linker-generated)
|
||||||
|| symbol.section.is_none()
|
|| symbol.section.is_none()
|
||||||
|
|
Loading…
Reference in New Issue