Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Try to guess symbol address in Wasm #539

Merged
merged 4 commits into from
May 5, 2023
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 26 additions & 1 deletion src/read/wasm.rs
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,8 @@ impl<'data, R: ReadRef<'data>> WasmFile<'data, R> {
let mut entry_func_id = None;
let mut code_range_start = 0;
let mut code_func_index = 0;
// One-to-one mapping of globals to their value (if the global is a constant integer).
let mut global_values = Vec::new();

for payload in parser {
let payload = payload.read_error("Invalid Wasm section header")?;
Expand Down Expand Up @@ -168,6 +170,20 @@ impl<'data, R: ReadRef<'data>> WasmFile<'data, R> {
}
wp::Payload::GlobalSection(section) => {
file.add_section(SectionId::Global, section.range(), "");
for global in section {
let global = global.read_error("Couldn't read a global item")?;
let mut address = None;
if !global.ty.mutable {
// There should be exactly one instruction.
let init = global.init_expr.get_operators_reader().read();
address = match init.read_error("Couldn't read a global init expr")? {
wp::Operator::I32Const { value } => Some(value as u64),
wp::Operator::I64Const { value } => Some(value as u64),
_ => None,
};
}
global_values.push(address);
}
}
wp::Payload::ExportSection(section) => {
file.add_section(SectionId::Export, section.range(), "");
Expand Down Expand Up @@ -205,9 +221,18 @@ impl<'data, R: ReadRef<'data>> WasmFile<'data, R> {
wp::ExternalKind::Tag => continue,
};

// Try to guess the symbol address. Rust and C export a global containing
// the address in linear memory of the symbol.
let mut address = 0;
if export.kind == wp::ExternalKind::Global {
if let Some(&Some(x)) = global_values.get(export.index as usize) {
address = x;
}
}

file.symbols.push(WasmSymbolInternal {
name: export.name,
address: 0,
address,
size: 0,
kind,
section: SymbolSection::Section(SectionIndex(section_idx as usize)),
Expand Down