From 1060fd4c721ae54b0cdce2b7c5590d15d13ef7fa Mon Sep 17 00:00:00 2001 From: gingerBill Date: Thu, 18 Jun 2026 15:21:05 +0100 Subject: [PATCH] Factor out reloc group logic --- core/rexcode/wasm/module/module.odin | 2 ++ core/rexcode/wasm/module/parse.odin | 5 +++ core/rexcode/wasm/module/print.odin | 19 ++-------- core/rexcode/wasm/module/print_wat.odin | 47 ++++++------------------- core/rexcode/wasm/module/relocs.odin | 10 ++++++ 5 files changed, 30 insertions(+), 53 deletions(-) diff --git a/core/rexcode/wasm/module/module.odin b/core/rexcode/wasm/module/module.odin index e42c3b1d7..f27e819d3 100644 --- a/core/rexcode/wasm/module/module.odin +++ b/core/rexcode/wasm/module/module.odin @@ -98,6 +98,8 @@ Module :: struct { exports: []Export, start: i64, // -1 if absent, else the start funcidx + reloc_groups: []Reloc_Group, + data: []u8, // borrowed reference to the whole file (body decode reads from it) allocator: runtime.Allocator, diff --git a/core/rexcode/wasm/module/parse.odin b/core/rexcode/wasm/module/parse.odin index 1384a0292..a77a07449 100644 --- a/core/rexcode/wasm/module/parse.odin +++ b/core/rexcode/wasm/module/parse.odin @@ -196,6 +196,9 @@ parse :: proc(data: []u8, allocator := context.allocator) -> (m: Module, err: Re build_functions(&m, func_typeidx, codes, allocator) or_return apply_name_section(&m) + + m.reloc_groups = parse_relocations(m, allocator) or_return + return } @@ -486,6 +489,8 @@ apply_name_section :: proc(m: ^Module) { } module_destroy :: proc(m: ^Module) { + relocations_destroy(m.reloc_groups, m.allocator) + for t in m.types { delete(t.params, m.allocator) delete(t.results, m.allocator) diff --git a/core/rexcode/wasm/module/print.odin b/core/rexcode/wasm/module/print.odin index 4195a02ab..6097f335b 100644 --- a/core/rexcode/wasm/module/print.odin +++ b/core/rexcode/wasm/module/print.odin @@ -54,8 +54,6 @@ sbprint_module :: proc(sb: ^strings.Builder, m: Module) { } } - relocs_group, _ := parse_relocations(m, context.temp_allocator) - // sections for sec in m.sections { write_padded :: proc(sb: ^strings.Builder, s: string, width: int) { @@ -133,14 +131,7 @@ sbprint_module :: proc(sb: ^strings.Builder, m: Module) { } fallthrough case 0: // expr + bytes - relocs: []wasm.Relocation - for rg in relocs_group { - if rg.target_section == sec.id { - relocs = rg.relocs - break - } - } - + relocs := relocations_from_section_id(m.reloc_groups, sec.id) for r.off < u32(len(r.data)) { inst, info, next := wasm.decode_one(r.data[r.off:], relocs=relocs, pc=0, targets_allocator=context.temp_allocator) or_break section_printing r.off += next @@ -211,13 +202,7 @@ sbprint_module :: proc(sb: ^strings.Builder, m: Module) { // } - func_relocs: []wasm.Relocation - for rg in relocs_group { - if rg.target_section == .FUNCTION { - func_relocs = rg.relocs - break - } - } + func_relocs := relocations_from_section_id(m.reloc_groups, .FUNCTION) for f in m.functions { if f.exported { diff --git a/core/rexcode/wasm/module/print_wat.odin b/core/rexcode/wasm/module/print_wat.odin index 18832045e..1f9e719aa 100644 --- a/core/rexcode/wasm/module/print_wat.odin +++ b/core/rexcode/wasm/module/print_wat.odin @@ -115,14 +115,7 @@ sbprint_wat :: proc(sb: ^strings.Builder, m: Module, opts := DEFAULT_WAT_OPTIONS wat_write_imports(sb, m, unit) - relocs_group, _ := parse_relocations(m, context.temp_allocator) - func_relocs: []wasm.Relocation - for rg in relocs_group { - if rg.target_section == .FUNCTION { - func_relocs = rg.relocs - break - } - } + func_relocs := relocations_from_section_id(m.reloc_groups, .FUNCTION) for f in m.functions { if f.imported { @@ -133,7 +126,7 @@ sbprint_wat :: proc(sb: ^strings.Builder, m: Module, opts := DEFAULT_WAT_OPTIONS wat_write_tables (sb, m, unit) wat_write_memories(sb, m, unit) - wat_write_globals (sb, m, relocs_group, unit) + wat_write_globals (sb, m, unit) for e in m.exports { fmt.sbprintf(sb, "%s(export %q (%s %d))\n", unit, e.name, external_kind_name(e.kind), e.index) @@ -143,8 +136,8 @@ sbprint_wat :: proc(sb: ^strings.Builder, m: Module, opts := DEFAULT_WAT_OPTIONS fmt.sbprintf(sb, "%s(start %d)\n", unit, m.start) } - wat_write_elements(sb, m, relocs_group, unit) - wat_write_data (sb, m, relocs_group, unit) + wat_write_elements(sb, m, unit) + wat_write_data (sb, m, unit) } wat_write_functype :: proc(sb: ^strings.Builder, t: Func_Type) { @@ -526,19 +519,13 @@ wat_write_memories :: proc(sb: ^strings.Builder, m: Module, unit: string) { } } -wat_write_globals :: proc(sb: ^strings.Builder, m: Module, relocs_group: []Reloc_Group, unit: string) { +wat_write_globals :: proc(sb: ^strings.Builder, m: Module, unit: string) { idx := count_import_kind(m, .GLOBAL) for sec in m.sections { if sec.id != .GLOBAL { continue } - relocs: []wasm.Relocation - for rg in relocs_group { - if rg.target_section == sec.id { - relocs = rg.relocs - break - } - } + relocs := relocations_from_section_id(m.reloc_groups, sec.id) r := reader(m.data, sec.offset) count := rd_u32(&r) or_break @@ -560,19 +547,14 @@ wat_write_globals :: proc(sb: ^strings.Builder, m: Module, relocs_group: []Reloc } } -wat_write_elements :: proc(sb: ^strings.Builder, m: Module, relocs_group: []Reloc_Group, unit: string) -> Parse_Error { +wat_write_elements :: proc(sb: ^strings.Builder, m: Module, unit: string) -> Parse_Error { elem_idx := 0 for sec in m.sections { if sec.id != .ELEMENT { continue } - relocs: []wasm.Relocation - for rg in relocs_group { - if rg.target_section == sec.id { - relocs = rg.relocs - break - } - } + + relocs := relocations_from_section_id(m.reloc_groups, sec.id) r := reader(m.data, sec.offset) count := rd_u32(&r) or_break @@ -599,7 +581,7 @@ wat_write_elements :: proc(sb: ^strings.Builder, m: Module, relocs_group: []Relo return nil } -wat_write_data :: proc(sb: ^strings.Builder, m: Module, relocs_group: []Reloc_Group, unit: string) -> Parse_Error { +wat_write_data :: proc(sb: ^strings.Builder, m: Module, unit: string) -> Parse_Error { data_idx := 0 for sec in m.sections { if sec.id != .DATA { @@ -620,19 +602,12 @@ wat_write_data :: proc(sb: ^strings.Builder, m: Module, relocs_group: []Reloc_Gr memidx, _ = rd_u32(&r) fallthrough case 0: - relocs: []wasm.Relocation - for rg in relocs_group { - if rg.target_section == sec.id { - relocs = rg.relocs - break - } - } - // expr + bytes if memidx != 0 { fmt.sbprintf(sb, " (memory %d)", memidx) } strings.write_byte(sb, ' ') + relocs := relocations_from_section_id(m.reloc_groups, sec.id) wat_write_const_expr(sb, m, relocs, m.data, &r.off, unit, context.temp_allocator) case 1: // bytes diff --git a/core/rexcode/wasm/module/relocs.odin b/core/rexcode/wasm/module/relocs.odin index e350d8cf7..127d59908 100644 --- a/core/rexcode/wasm/module/relocs.odin +++ b/core/rexcode/wasm/module/relocs.odin @@ -57,6 +57,16 @@ relocations_destroy :: proc(groups: []Reloc_Group, allocator: runtime.Allocator) delete(groups) } +@(require_results) +relocations_from_section_id :: proc(reloc_groups: []Reloc_Group, sec_id: Section_Id) -> []wasm.Relocation { + for rg in reloc_groups { + if rg.target_section == sec_id { + return rg.relocs + } + } + return nil +} + @(require_results) reloc_type_from_wire :: proc(code: u8) -> (wasm.Relocation_Type, bool) { switch code {