| ... | ... | @@ -679,7 +679,11 @@ pub fn finish(f: *Flush, wasm: *Wasm) !void { |
| 679 | 679 | for (wasm.functions.keys()) |resolution| switch (resolution.unpack(wasm)) { |
| 680 | 680 | .unresolved => unreachable, |
| 681 | 681 | .__wasm_apply_global_tls_relocs => @panic("TODO lower __wasm_apply_global_tls_relocs"), |
| 682 | | .__wasm_call_ctors => @panic("TODO lower __wasm_call_ctors"), |
| 682 | .__wasm_call_ctors => { |
| 683 | const code_start = try reserveSize(gpa, binary_bytes); |
| 684 | defer replaceSize(binary_bytes, code_start); |
| 685 | try emitCallCtorsFunction(wasm, binary_bytes); |
| 686 | }, |
| 683 | 687 | .__wasm_init_memory => @panic("TODO lower __wasm_init_memory "), |
| 684 | 688 | .__wasm_init_tls => @panic("TODO lower __wasm_init_tls "), |
| 685 | 689 | .object_function => |i| { |
| ... | ... | @@ -1559,3 +1563,27 @@ fn reloc_leb_table(code: []u8, table: Wasm.TableIndex) void { |
| 1559 | 1563 | fn reloc_leb_type(code: []u8, index: Wasm.FunctionType.Index) void { |
| 1560 | 1564 | leb.writeUnsignedFixed(5, code[0..5], @intFromEnum(index)); |
| 1561 | 1565 | } |
| 1566 | |
| 1567 | fn emitCallCtorsFunction(wasm: *const Wasm, binary_bytes: *std.ArrayListUnmanaged(u8)) Allocator.Error!void { |
| 1568 | const gpa = wasm.base.comp.gpa; |
| 1569 | |
| 1570 | try binary_bytes.ensureUnusedCapacity(gpa, 5 + 1); |
| 1571 | leb.writeUleb128(binary_bytes.fixedWriter(), @as(u32, 0)) catch unreachable; // no locals |
| 1572 | |
| 1573 | for (wasm.object_init_funcs.items) |init_func| { |
| 1574 | const func = init_func.function_index.ptr(wasm); |
| 1575 | const ty = func.type_index.ptr(wasm); |
| 1576 | const n_returns = ty.returns.slice(wasm).len; |
| 1577 | |
| 1578 | // Call function by its function index |
| 1579 | try binary_bytes.ensureUnusedCapacity(gpa, 1 + 5 + n_returns + 1); |
| 1580 | const call_index: Wasm.OutputFunctionIndex = .fromObjectFunction(wasm, init_func.function_index); |
| 1581 | binary_bytes.appendAssumeCapacity(@intFromEnum(std.wasm.Opcode.call)); |
| 1582 | leb.writeUleb128(binary_bytes.fixedWriter(), @intFromEnum(call_index)) catch unreachable; |
| 1583 | |
| 1584 | // drop all returned values from the stack as __wasm_call_ctors has no return value |
| 1585 | binary_bytes.appendNTimesAssumeCapacity(@intFromEnum(std.wasm.Opcode.drop), n_returns); |
| 1586 | } |
| 1587 | |
| 1588 | binary_bytes.appendAssumeCapacity(@intFromEnum(std.wasm.Opcode.end)); // end function body |
| 1589 | } |