mirror of
https://codeberg.org/ziglang/zig.git
synced 2025-12-06 13:54:21 +00:00
Elf2: fix relocations against untyped symbols
This commit is contained in:
parent
8647e4d311
commit
79a9f3a418
1 changed files with 20 additions and 21 deletions
|
|
@ -1444,15 +1444,9 @@ pub fn symtabSlice(elf: *Elf) SymtabSlice {
|
||||||
const slice = elf.si.symtab.node(elf).slice(&elf.mf);
|
const slice = elf.si.symtab.node(elf).slice(&elf.mf);
|
||||||
return switch (elf.identClass()) {
|
return switch (elf.identClass()) {
|
||||||
.NONE, _ => unreachable,
|
.NONE, _ => unreachable,
|
||||||
inline else => |class| @unionInit(
|
inline else => |class| @unionInit(SymtabSlice, @tagName(class), @ptrCast(@alignCast(
|
||||||
SymtabSlice,
|
slice[0..std.mem.alignBackwardAnyAlign(usize, slice.len, @sizeOf(class.ElfN().Sym))],
|
||||||
@tagName(class),
|
))),
|
||||||
@ptrCast(@alignCast(slice[0..std.mem.alignBackwardAnyAlign(
|
|
||||||
usize,
|
|
||||||
slice.len,
|
|
||||||
@sizeOf(class.ElfN().Sym),
|
|
||||||
)])),
|
|
||||||
),
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1471,11 +1465,9 @@ pub fn dynsymSlice(elf: *Elf) SymtabSlice {
|
||||||
const slice = elf.si.dynsym.node(elf).slice(&elf.mf);
|
const slice = elf.si.dynsym.node(elf).slice(&elf.mf);
|
||||||
return switch (elf.identClass()) {
|
return switch (elf.identClass()) {
|
||||||
.NONE, _ => unreachable,
|
.NONE, _ => unreachable,
|
||||||
inline else => |class| @unionInit(
|
inline else => |class| @unionInit(SymtabSlice, @tagName(class), @ptrCast(@alignCast(
|
||||||
SymtabSlice,
|
slice[0..std.mem.alignBackwardAnyAlign(usize, slice.len, @sizeOf(class.ElfN().Sym))],
|
||||||
@tagName(class),
|
))),
|
||||||
@ptrCast(@alignCast(slice)),
|
|
||||||
),
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1853,7 +1845,7 @@ fn loadObject(
|
||||||
break :strtab strtab;
|
break :strtab strtab;
|
||||||
};
|
};
|
||||||
defer gpa.free(strtab);
|
defer gpa.free(strtab);
|
||||||
const symnum = std.math.divExact(
|
const symnum = std.math.sub(u32, std.math.divExact(
|
||||||
u32,
|
u32,
|
||||||
@intCast(symtab.shdr.size),
|
@intCast(symtab.shdr.size),
|
||||||
@intCast(symtab.shdr.entsize),
|
@intCast(symtab.shdr.entsize),
|
||||||
|
|
@ -1861,9 +1853,9 @@ fn loadObject(
|
||||||
path,
|
path,
|
||||||
"symtab section size (0x{x}) is not a multiple of entsize (0x{x})",
|
"symtab section size (0x{x}) is not a multiple of entsize (0x{x})",
|
||||||
.{ symtab.shdr.size, symtab.shdr.entsize },
|
.{ symtab.shdr.size, symtab.shdr.entsize },
|
||||||
);
|
), 1) catch continue;
|
||||||
symmap.clearRetainingCapacity();
|
symmap.clearRetainingCapacity();
|
||||||
try symmap.resize(gpa, std.math.sub(u32, symnum, 1) catch continue);
|
try symmap.resize(gpa, symnum);
|
||||||
try elf.symtab.ensureUnusedCapacity(gpa, symnum);
|
try elf.symtab.ensureUnusedCapacity(gpa, symnum);
|
||||||
try elf.globals.ensureUnusedCapacity(gpa, symnum);
|
try elf.globals.ensureUnusedCapacity(gpa, symnum);
|
||||||
try fr.seekTo(fl.offset + symtab.shdr.offset + symtab.shdr.entsize);
|
try fr.seekTo(fl.offset + symtab.shdr.offset + symtab.shdr.entsize);
|
||||||
|
|
@ -1874,13 +1866,13 @@ fn loadObject(
|
||||||
if (input_sym.name >= strtab.len or input_sym.shndx == std.elf.SHN_UNDEF or
|
if (input_sym.name >= strtab.len or input_sym.shndx == std.elf.SHN_UNDEF or
|
||||||
input_sym.shndx >= ehdr.shnum) continue;
|
input_sym.shndx >= ehdr.shnum) continue;
|
||||||
switch (input_sym.info.type) {
|
switch (input_sym.info.type) {
|
||||||
else => continue,
|
.NOTYPE, .OBJECT, .FUNC => {},
|
||||||
.SECTION => {
|
.SECTION => {
|
||||||
const section = §ions[input_sym.shndx];
|
const section = §ions[input_sym.shndx];
|
||||||
if (input_sym.value == section.shdr.addr) si.* = section.si;
|
if (input_sym.value == section.shdr.addr) si.* = section.si;
|
||||||
continue;
|
continue;
|
||||||
},
|
},
|
||||||
.OBJECT, .FUNC => {},
|
else => continue,
|
||||||
}
|
}
|
||||||
const name = std.mem.sliceTo(strtab[input_sym.name..], 0);
|
const name = std.mem.sliceTo(strtab[input_sym.name..], 0);
|
||||||
const parent_si = sections[input_sym.shndx].si;
|
const parent_si = sections[input_sym.shndx].si;
|
||||||
|
|
@ -1935,8 +1927,13 @@ fn loadObject(
|
||||||
};
|
};
|
||||||
if (rels.shdr.entsize < @sizeOf(Rel))
|
if (rels.shdr.entsize < @sizeOf(Rel))
|
||||||
return diags.failParse(path, "unsupported rel entsize", .{});
|
return diags.failParse(path, "unsupported rel entsize", .{});
|
||||||
|
|
||||||
const loc_sec = §ions[rels.shdr.info];
|
const loc_sec = §ions[rels.shdr.info];
|
||||||
if (loc_sec.si == .null) continue;
|
if (loc_sec.si == .null) continue;
|
||||||
|
const loc_sym = loc_sec.si.get(elf);
|
||||||
|
assert(loc_sym.loc_relocs == .none);
|
||||||
|
loc_sym.loc_relocs = @enumFromInt(elf.relocs.items.len);
|
||||||
|
|
||||||
const relnum = std.math.divExact(
|
const relnum = std.math.divExact(
|
||||||
u32,
|
u32,
|
||||||
@intCast(rels.shdr.size),
|
@intCast(rels.shdr.size),
|
||||||
|
|
@ -1951,7 +1948,7 @@ fn loadObject(
|
||||||
for (0..relnum) |_| {
|
for (0..relnum) |_| {
|
||||||
const rel = try r.peekStruct(Rel, target_endian);
|
const rel = try r.peekStruct(Rel, target_endian);
|
||||||
try r.discardAll64(rels.shdr.entsize);
|
try r.discardAll64(rels.shdr.entsize);
|
||||||
if (rel.info.sym >= symnum) continue;
|
if (rel.info.sym == 0 or rel.info.sym > symnum) continue;
|
||||||
const target_si = symmap.items[rel.info.sym - 1];
|
const target_si = symmap.items[rel.info.sym - 1];
|
||||||
if (target_si == .null) continue;
|
if (target_si == .null) continue;
|
||||||
elf.addRelocAssumeCapacity(
|
elf.addRelocAssumeCapacity(
|
||||||
|
|
@ -2854,10 +2851,12 @@ fn flushInputSection(elf: *Elf, isi: Node.InputSectionIndex) !void {
|
||||||
var fr = file.reader(comp.io, &.{});
|
var fr = file.reader(comp.io, &.{});
|
||||||
try fr.seekTo(file_loc.offset);
|
try fr.seekTo(file_loc.offset);
|
||||||
var nw: MappedFile.Node.Writer = undefined;
|
var nw: MappedFile.Node.Writer = undefined;
|
||||||
isi.symbol(elf).node(elf).writer(&elf.mf, gpa, &nw);
|
const si = isi.symbol(elf);
|
||||||
|
si.node(elf).writer(&elf.mf, gpa, &nw);
|
||||||
defer nw.deinit();
|
defer nw.deinit();
|
||||||
if (try nw.interface.sendFileAll(&fr, .limited(@intCast(file_loc.size))) != file_loc.size)
|
if (try nw.interface.sendFileAll(&fr, .limited(@intCast(file_loc.size))) != file_loc.size)
|
||||||
return error.EndOfStream;
|
return error.EndOfStream;
|
||||||
|
si.applyLocationRelocs(elf);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn flushFileOffset(elf: *Elf, ni: MappedFile.Node.Index) !void {
|
fn flushFileOffset(elf: *Elf, ni: MappedFile.Node.Index) !void {
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue