| ... | @@ -871,6 +871,22 @@ fn resolveLazySymbols(wasm: *Wasm) !void { | ... | @@ -871,6 +871,22 @@ fn resolveLazySymbols(wasm: *Wasm) !void { |
| 871 | try wasm.parseAtom(atom, .{ .data = .synthetic }); | 871 | try wasm.parseAtom(atom, .{ .data = .synthetic }); |
| 872 | try wasm.symbol_atom.putNoClobber(wasm.base.allocator, loc, atom); | 872 | try wasm.symbol_atom.putNoClobber(wasm.base.allocator, loc, atom); |
| 873 | } | 873 | } |
| | 874 | |
| | 875 | if (wasm.undefs.fetchSwapRemove("__heap_end")) |kv| { |
| | 876 | const loc = try wasm.createSyntheticSymbol("__heap_end", .data); |
| | 877 | try wasm.discarded.putNoClobber(wasm.base.allocator, kv.value, loc); |
| | 878 | _ = wasm.resolved_symbols.swapRemove(loc); |
| | 879 | |
| | 880 | const atom = try wasm.base.allocator.create(Atom); |
| | 881 | errdefer wasm.base.allocator.destroy(atom); |
| | 882 | try wasm.managed_atoms.append(wasm.base.allocator, atom); |
| | 883 | atom.* = Atom.empty; |
| | 884 | atom.sym_index = loc.index; |
| | 885 | atom.alignment = 1; |
| | 886 | |
| | 887 | try wasm.parseAtom(atom, .{ .data = .synthetic }); |
| | 888 | try wasm.symbol_atom.putNoClobber(wasm.base.allocator, loc, atom); |
| | 889 | } |
| 874 | } | 890 | } |
| 875 | | 891 | |
| 876 | // Tries to find a global symbol by its name. Returns null when not found, | 892 | // Tries to find a global symbol by its name. Returns null when not found, |
| ... | @@ -892,14 +908,8 @@ fn checkUndefinedSymbols(wasm: *const Wasm) !void { | ... | @@ -892,14 +908,8 @@ fn checkUndefinedSymbols(wasm: *const Wasm) !void { |
| 892 | const file_name = if (undef.file) |file_index| name: { | 908 | const file_name = if (undef.file) |file_index| name: { |
| 893 | break :name wasm.objects.items[file_index].name; | 909 | break :name wasm.objects.items[file_index].name; |
| 894 | } else wasm.name; | 910 | } else wasm.name; |
| 895 | const import_name = if (undef.file) |file_index| name: { | 911 | const symbol_name = undef.getName(wasm); |
| 896 | const obj = wasm.objects.items[file_index]; | 912 | log.err("could not resolve undefined symbol '{s}'", .{symbol_name}); |
| 897 | const name_index = if (symbol.tag == .function) name_index: { | | |
| 898 | break :name_index obj.findImport(symbol.tag.externalType(), symbol.index).name; | | |
| 899 | } else symbol.name; | | |
| 900 | break :name obj.string_table.get(name_index); | | |
| 901 | } else wasm.string_table.get(wasm.imports.get(undef).?.name); | | |
| 902 | log.err("could not resolve undefined symbol '{s}'", .{import_name}); | | |
| 903 | log.err(" defined in '{s}'", .{file_name}); | 913 | log.err(" defined in '{s}'", .{file_name}); |
| 904 | } | 914 | } |
| 905 | } | 915 | } |
| ... | @@ -2223,12 +2233,20 @@ fn setupMemory(wasm: *Wasm) !void { | ... | @@ -2223,12 +2233,20 @@ fn setupMemory(wasm: *Wasm) !void { |
| 2223 | } | 2233 | } |
| 2224 | memory_ptr = initial_memory; | 2234 | memory_ptr = initial_memory; |
| 2225 | } | 2235 | } |
| 2226 | | 2236 | memory_ptr = mem.alignForwardGeneric(u64, memory_ptr, std.wasm.page_size); |
| 2227 | // In case we do not import memory, but define it ourselves, | 2237 | // In case we do not import memory, but define it ourselves, |
| 2228 | // set the minimum amount of pages on the memory section. | 2238 | // set the minimum amount of pages on the memory section. |
| 2229 | wasm.memories.limits.min = @intCast(u32, std.mem.alignForwardGeneric(u64, memory_ptr, page_size) / page_size); | 2239 | wasm.memories.limits.min = @intCast(u32, memory_ptr / page_size); |
| 2230 | log.debug("Total memory pages: {d}", .{wasm.memories.limits.min}); | 2240 | log.debug("Total memory pages: {d}", .{wasm.memories.limits.min}); |
| 2231 | | 2241 | |
| | 2242 | if (wasm.findGlobalSymbol("__heap_end")) |loc| { |
| | 2243 | const segment_index = wasm.data_segments.get(".synthetic").?; |
| | 2244 | const segment = &wasm.segments.items[segment_index]; |
| | 2245 | segment.offset = 0; |
| | 2246 | const atom = wasm.symbol_atom.get(loc).?; |
| | 2247 | atom.offset = @intCast(u32, memory_ptr); |
| | 2248 | } |
| | 2249 | |
| 2232 | if (wasm.base.options.max_memory) |max_memory| { | 2250 | if (wasm.base.options.max_memory) |max_memory| { |
| 2233 | if (!std.mem.isAlignedGeneric(u64, max_memory, page_size)) { | 2251 | if (!std.mem.isAlignedGeneric(u64, max_memory, page_size)) { |
| 2234 | log.err("Maximum memory must be {d}-byte aligned", .{page_size}); | 2252 | log.err("Maximum memory must be {d}-byte aligned", .{page_size}); |
| ... | @@ -3392,6 +3410,8 @@ fn emitNameSection(wasm: *Wasm, binary_bytes: *std.ArrayList(u8), arena: std.mem | ... | @@ -3392,6 +3410,8 @@ fn emitNameSection(wasm: *Wasm, binary_bytes: *std.ArrayList(u8), arena: std.mem |
| 3392 | // bss section is not emitted when this condition holds true, so we also | 3410 | // bss section is not emitted when this condition holds true, so we also |
| 3393 | // do not output a name for it. | 3411 | // do not output a name for it. |
| 3394 | if (!wasm.base.options.import_memory and std.mem.eql(u8, key, ".bss")) continue; | 3412 | if (!wasm.base.options.import_memory and std.mem.eql(u8, key, ".bss")) continue; |
| | 3413 | // Synthetic segments are not emitted |
| | 3414 | if (std.mem.eql(u8, key, ".synthetic")) continue; |
| 3395 | segments.appendAssumeCapacity(.{ .index = data_segment_index, .name = key }); | 3415 | segments.appendAssumeCapacity(.{ .index = data_segment_index, .name = key }); |
| 3396 | data_segment_index += 1; | 3416 | data_segment_index += 1; |
| 3397 | } | 3417 | } |