wasm: create relocations for extern decls

This also fixes performing relocations for data symbols
of which the target symbol exists in an external object file.
We do this by checking if the target symbol was discarded,
and if so: get the new location so that we can find the
corresponding atom that belongs to said new location. Previously
it would always assume the symbol would live in the same file
as the atom/symbol that is doing the relocation.
This commit is contained in:
Luuk de Gram
2022-08-26 08:11:17 +02:00
parent 414fcea162
commit 4f72ac265a
2 changed files with 6 additions and 7 deletions

View File

@@ -2355,7 +2355,7 @@ fn lowerDeclRefValue(self: *Self, tv: TypedValue, decl_index: Module.Decl.Index)
const module = self.bin_file.base.options.module.?;
const decl = module.declPtr(decl_index);
if (decl.ty.zigTypeTag() != .Fn and !decl.ty.hasRuntimeBitsIgnoreComptime()) {
if (!decl.ty.hasRuntimeBitsIgnoreComptime()) {
return WValue{ .imm32 = 0xaaaaaaaa };
}
@@ -2394,9 +2394,7 @@ fn lowerConstant(self: *Self, val: Value, ty: Type) InnerError!WValue {
const decl_index = decl_ref_mut.data.decl_index;
return self.lowerDeclRefValue(.{ .ty = ty, .val = val }, decl_index);
}
const target = self.target;
switch (ty.zigTypeTag()) {
.Void => return WValue{ .none = {} },
.Int => {

View File

@@ -174,13 +174,14 @@ fn relocationValue(self: Atom, relocation: types.Relocation, wasm_bin: *const Wa
=> {
std.debug.assert(symbol.tag == .data and !symbol.isUndefined());
const merge_segment = wasm_bin.base.options.output_mode != .Obj;
const segment_info = if (self.file) |object_index| blk: {
const target_atom_loc = wasm_bin.discarded.get(target_loc) orelse target_loc;
const target_atom = wasm_bin.symbol_atom.get(target_atom_loc).?;
const segment_info = if (target_atom.file) |object_index| blk: {
break :blk wasm_bin.objects.items[object_index].segment_info;
} else wasm_bin.segment_info.items;
const segment_name = segment_info[symbol.index].outputName(merge_segment);
const atom_index = wasm_bin.data_segments.get(segment_name).?;
const target_atom = wasm_bin.symbol_atom.get(target_loc).?;
const segment = wasm_bin.segments.items[atom_index];
const segment_index = wasm_bin.data_segments.get(segment_name).?;
const segment = wasm_bin.segments.items[segment_index];
return target_atom.offset + segment.offset + (relocation.addend orelse 0);
},
.R_WASM_EVENT_INDEX_LEB => return symbol.index,