Commit 57889cae80
Changed files (8)
lib
std
lib/std/debug/SelfInfo/Elf.zig
@@ -441,11 +441,11 @@ const DlIterContext = struct {
// Populate `build_id` and `gnu_eh_frame`
for (info.phdr[0..info.phnum]) |phdr| {
- switch (phdr.p_type) {
- std.elf.PT_NOTE => {
+ switch (phdr.type) {
+ .NOTE => {
// Look for .note.gnu.build-id
- const segment_ptr: [*]const u8 = @ptrFromInt(info.addr + phdr.p_vaddr);
- var r: std.Io.Reader = .fixed(segment_ptr[0..phdr.p_memsz]);
+ const segment_ptr: [*]const u8 = @ptrFromInt(info.addr + phdr.vaddr);
+ var r: std.Io.Reader = .fixed(segment_ptr[0..phdr.memsz]);
const name_size = r.takeInt(u32, native_endian) catch continue;
const desc_size = r.takeInt(u32, native_endian) catch continue;
const note_type = r.takeInt(u32, native_endian) catch continue;
@@ -455,9 +455,9 @@ const DlIterContext = struct {
const desc = r.take(desc_size) catch continue;
build_id = desc;
},
- std.elf.PT_GNU_EH_FRAME => {
- const segment_ptr: [*]const u8 = @ptrFromInt(info.addr + phdr.p_vaddr);
- gnu_eh_frame = segment_ptr[0..phdr.p_memsz];
+ std.elf.PT.GNU_EH_FRAME => {
+ const segment_ptr: [*]const u8 = @ptrFromInt(info.addr + phdr.vaddr);
+ gnu_eh_frame = segment_ptr[0..phdr.memsz];
},
else => {},
}
@@ -478,11 +478,11 @@ const DlIterContext = struct {
});
for (info.phdr[0..info.phnum]) |phdr| {
- if (phdr.p_type != std.elf.PT_LOAD) continue;
+ if (phdr.type != .LOAD) continue;
try context.si.ranges.append(gpa, .{
// Overflowing addition handles VSDOs having p_vaddr = 0xffffffffff700000
- .start = info.addr +% phdr.p_vaddr,
- .len = phdr.p_memsz,
+ .start = info.addr +% phdr.vaddr,
+ .len = phdr.memsz,
.module_index = module_index,
});
}
lib/std/os/linux.zig
@@ -6101,7 +6101,7 @@ pub const dirent64 = extern struct {
pub const dl_phdr_info = extern struct {
addr: usize,
name: ?[*:0]const u8,
- phdr: [*]std.elf.Phdr,
+ phdr: [*]std.elf.ElfN.Phdr,
phnum: u16,
};
lib/std/posix/test.zig
@@ -257,11 +257,11 @@ fn iter_fn(info: *dl_phdr_info, size: usize, counter: *usize) IterFnError!void {
while (i < info.phnum) : (i += 1) {
const phdr = info.phdr[i];
- if (phdr.p_type != elf.PT_LOAD) continue;
+ if (phdr.type != .LOAD) continue;
- const reloc_addr = info.addr + phdr.p_vaddr;
+ const reloc_addr = info.addr + phdr.vaddr;
// Find the ELF header
- const elf_header = @as(*elf.Ehdr, @ptrFromInt(reloc_addr - phdr.p_offset));
+ const elf_header = @as(*elf.Ehdr, @ptrFromInt(reloc_addr - phdr.offset));
// Validate the magic
if (!mem.eql(u8, elf_header.e_ident[0..4], elf.MAGIC)) return error.BadElfMagic;
// Consistency check
lib/std/c.zig
@@ -3971,7 +3971,7 @@ pub const dl_phdr_info = switch (native_os) {
/// Module name.
name: ?[*:0]const u8,
/// Pointer to module's phdr.
- phdr: [*]std.elf.Phdr,
+ phdr: [*]std.elf.ElfN.Phdr,
/// Number of entries in phdr.
phnum: u16,
/// Total number of loads.
@@ -3984,7 +3984,7 @@ pub const dl_phdr_info = switch (native_os) {
.illumos => extern struct {
addr: std.elf.Addr,
name: ?[*:0]const u8,
- phdr: [*]std.elf.Phdr,
+ phdr: [*]std.elf.ElfN.Phdr,
phnum: std.elf.Half,
/// Incremented when a new object is mapped into the process.
adds: u64,
@@ -3995,7 +3995,7 @@ pub const dl_phdr_info = switch (native_os) {
.openbsd, .haiku, .dragonfly, .netbsd, .serenity => extern struct {
addr: usize,
name: ?[*:0]const u8,
- phdr: [*]std.elf.Phdr,
+ phdr: [*]std.elf.ElfN.Phdr,
phnum: std.elf.Half,
},
else => void,
lib/std/dynamic_library.zig
@@ -92,8 +92,7 @@ pub fn get_DYNAMIC() ?[*]const elf.Dyn {
});
}
-pub fn linkmap_iterator(phdrs: []const elf.Phdr) error{InvalidExe}!LinkMap.Iterator {
- _ = phdrs;
+pub fn linkmap_iterator() error{InvalidExe}!LinkMap.Iterator {
const _DYNAMIC = get_DYNAMIC() orelse {
// No PT_DYNAMIC means this is a statically-linked non-PIE program.
return .{ .current = null };
lib/std/elf.zig
@@ -50,6 +50,7 @@ pub const AT_L2_CACHESIZE = 44;
pub const AT_L2_CACHEGEOMETRY = 45;
pub const AT_L3_CACHESIZE = 46;
pub const AT_L3_CACHEGEOMETRY = 47;
+pub const AT_MINSIGSTKSZ = 51;
pub const DT_NULL = 0;
pub const DT_NEEDED = 1;
lib/std/posix.zig
@@ -5048,6 +5048,13 @@ pub fn nanosleep(seconds: u64, nanoseconds: u64) void {
}
}
+pub fn getSelfPhdrs() []std.elf.ElfN.Phdr {
+ const getauxval = if (builtin.link_libc) std.c.getauxval else std.os.linux.getauxval;
+ assert(getauxval(std.elf.AT_PHENT) == @sizeOf(std.elf.ElfN.Phdr));
+ const phdrs: [*]std.elf.ElfN.Phdr = @ptrFromInt(getauxval(std.elf.AT_PHDR));
+ return phdrs[0..getauxval(std.elf.AT_PHNUM)];
+}
+
pub fn dl_iterate_phdr(
context: anytype,
comptime Error: type,
@@ -5075,34 +5082,24 @@ pub fn dl_iterate_phdr(
}
}
- const elf_base = std.process.getBaseAddress();
- const ehdr: *elf.Ehdr = @ptrFromInt(elf_base);
- // Make sure the base address points to an ELF image.
- assert(mem.eql(u8, ehdr.e_ident[0..4], elf.MAGIC));
- const n_phdr = ehdr.e_phnum;
- const phdrs = (@as([*]elf.Phdr, @ptrFromInt(elf_base + ehdr.e_phoff)))[0..n_phdr];
-
- var it = dl.linkmap_iterator(phdrs) catch unreachable;
+ var it = dl.linkmap_iterator() catch unreachable;
// The executable has no dynamic link segment, create a single entry for
// the whole ELF image.
if (it.end()) {
- // Find the base address for the ELF image, if this is a PIE the value
- // is non-zero.
- const base_address = for (phdrs) |*phdr| {
- if (phdr.p_type == elf.PT_PHDR) {
- break @intFromPtr(phdrs.ptr) - phdr.p_vaddr;
- // We could try computing the difference between _DYNAMIC and
- // the p_vaddr of the PT_DYNAMIC section, but using the phdr is
- // good enough (Is it?).
- }
- } else unreachable;
-
- var info = dl_phdr_info{
- .addr = base_address,
- .name = "/proc/self/exe",
+ const getauxval = if (builtin.link_libc) std.c.getauxval else std.os.linux.getauxval;
+ const phdrs = getSelfPhdrs();
+ var info: dl_phdr_info = .{
+ .addr = for (phdrs) |phdr| switch (phdr.type) {
+ .PHDR => break @intFromPtr(phdrs.ptr) - phdr.vaddr,
+ else => {},
+ } else unreachable,
+ .name = switch (getauxval(std.elf.AT_EXECFN)) {
+ 0 => "/proc/self/exe",
+ else => |name| @ptrFromInt(name),
+ },
.phdr = phdrs.ptr,
- .phnum = ehdr.e_phnum,
+ .phnum = @intCast(phdrs.len),
};
return callback(&info, @sizeOf(dl_phdr_info), context);
@@ -5110,24 +5107,18 @@ pub fn dl_iterate_phdr(
// Last return value from the callback function.
while (it.next()) |entry| {
- var phdr: [*]elf.Phdr = undefined;
- var phnum: u16 = undefined;
-
- if (entry.l_addr != 0) {
- const elf_header: *elf.Ehdr = @ptrFromInt(entry.l_addr);
- phdr = @ptrFromInt(entry.l_addr + elf_header.e_phoff);
- phnum = elf_header.e_phnum;
- } else {
- // This is the running ELF image
- phdr = @ptrFromInt(elf_base + ehdr.e_phoff);
- phnum = ehdr.e_phnum;
- }
-
- var info = dl_phdr_info{
+ const phdrs: []elf.ElfN.Phdr = if (entry.l_addr != 0) phdrs: {
+ const ehdr: *elf.ElfN.Ehdr = @ptrFromInt(entry.l_addr);
+ assert(mem.eql(u8, ehdr.ident[0..4], elf.MAGIC));
+ const phdrs: [*]elf.ElfN.Phdr = @ptrFromInt(entry.l_addr + ehdr.phoff);
+ break :phdrs phdrs[0..ehdr.phnum];
+ } else getSelfPhdrs();
+
+ var info: dl_phdr_info = .{
.addr = entry.l_addr,
.name = entry.l_name,
- .phdr = phdr,
- .phnum = phnum,
+ .phdr = phdrs.ptr,
+ .phnum = @intCast(phdrs.len),
};
try callback(&info, @sizeOf(dl_phdr_info), context);
lib/std/process.zig
@@ -1658,13 +1658,13 @@ fn posixGetUserInfoPasswdStream(name: []const u8, reader: *std.Io.Reader) !UserI
pub fn getBaseAddress() usize {
switch (native_os) {
.linux => {
- const getauxval = if (builtin.link_libc) std.c.getauxval else std.os.linux.getauxval;
- const base = getauxval(std.elf.AT_BASE);
- if (base != 0) {
- return base;
- }
- const phdr = getauxval(std.elf.AT_PHDR);
- return phdr - @sizeOf(std.elf.Ehdr);
+ const phdrs = std.posix.getSelfPhdrs();
+ var base: usize = 0;
+ for (phdrs) |phdr| switch (phdr.type) {
+ .LOAD => return base + phdr.vaddr,
+ .PHDR => base = @intFromPtr(phdrs.ptr) - phdr.vaddr,
+ else => {},
+ } else unreachable;
},
.driverkit, .ios, .macos, .tvos, .visionos, .watchos => {
return @intFromPtr(&std.c._mh_execute_header);