aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorJakub Konka <kubkon@jakubkonka.com>2023-08-26 08:13:41 +0200
committerJakub Konka <kubkon@jakubkonka.com>2023-08-29 11:39:34 +0200
commitb2773cd7120f7120410e1635aaeec026c7bbcdd1 (patch)
treecd7defea6ddbd23930c3e168b066cfbd75febe61 /src
parent180979ee41e7374ee1b8bc941e2281bb44e41dfd (diff)
downloadzig-b2773cd7120f7120410e1635aaeec026c7bbcdd1.tar.gz
zig-b2773cd7120f7120410e1635aaeec026c7bbcdd1.zip
macho: move initSection into MachO from Zld
Diffstat (limited to 'src')
-rw-r--r--src/link/MachO.zig50
-rw-r--r--src/link/MachO/Atom.zig46
-rw-r--r--src/link/MachO/Object.zig14
-rw-r--r--src/link/MachO/zld.zig42
4 files changed, 85 insertions, 67 deletions
diff --git a/src/link/MachO.zig b/src/link/MachO.zig
index 10961d145e..467b75c69c 100644
--- a/src/link/MachO.zig
+++ b/src/link/MachO.zig
@@ -2739,6 +2739,34 @@ fn calcPagezeroSize(self: *MachO) u64 {
return aligned_pagezero_vmsize;
}
+const InitSectionOpts = struct {
+ flags: u32 = macho.S_REGULAR,
+ reserved1: u32 = 0,
+ reserved2: u32 = 0,
+};
+
+pub fn initSection(
+ gpa: Allocator,
+ ctx: anytype,
+ segname: []const u8,
+ sectname: []const u8,
+ opts: InitSectionOpts,
+) !u8 {
+ log.debug("creating section '{s},{s}'", .{ segname, sectname });
+ const index = @as(u8, @intCast(ctx.sections.slice().len));
+ try ctx.sections.append(gpa, .{
+ .segment_index = undefined, // Segments will be created automatically later down the pipeline
+ .header = .{
+ .sectname = makeStaticString(sectname),
+ .segname = makeStaticString(segname),
+ .flags = opts.flags,
+ .reserved1 = opts.reserved1,
+ .reserved2 = opts.reserved2,
+ },
+ });
+ return index;
+}
+
fn allocateSection(self: *MachO, segname: []const u8, sectname: []const u8, opts: struct {
size: u64 = 0,
alignment: u32 = 0,
@@ -2751,7 +2779,6 @@ fn allocateSection(self: *MachO, segname: []const u8, sectname: []const u8, opts
// In incremental context, we create one section per segment pairing. This way,
// we can move the segment in raw file as we please.
const segment_id = @as(u8, @intCast(self.segments.items.len));
- const section_id = @as(u8, @intCast(self.sections.slice().len));
const vmaddr = blk: {
const prev_segment = self.segments.items[segment_id - 1];
break :blk mem.alignForward(u64, prev_segment.vmaddr + prev_segment.vmsize, page_size);
@@ -2782,23 +2809,18 @@ fn allocateSection(self: *MachO, segname: []const u8, sectname: []const u8, opts
.cmdsize = @sizeOf(macho.segment_command_64) + @sizeOf(macho.section_64),
};
- var section = macho.section_64{
- .sectname = makeStaticString(sectname),
- .segname = makeStaticString(segname),
- .addr = mem.alignForward(u64, vmaddr, opts.alignment),
- .offset = mem.alignForward(u32, @as(u32, @intCast(off)), opts.alignment),
- .size = opts.size,
- .@"align" = math.log2(opts.alignment),
+ const sect_id = try initSection(gpa, self, sectname, segname, .{
.flags = opts.flags,
.reserved2 = opts.reserved2,
- };
+ });
+ const section = &self.sections.items(.header)[sect_id];
+ section.addr = mem.alignForward(u64, vmaddr, opts.alignment);
+ section.offset = mem.alignForward(u32, @as(u32, @intCast(off)), opts.alignment);
+ section.size = opts.size;
+ section.@"align" = math.log2(opts.alignment);
assert(!section.isZerofill()); // TODO zerofill sections
- try self.sections.append(gpa, .{
- .segment_index = segment_id,
- .header = section,
- });
- return section_id;
+ return sect_id;
}
fn growSection(self: *MachO, sect_id: u8, needed_size: u64) !void {
diff --git a/src/link/MachO/Atom.zig b/src/link/MachO/Atom.zig
index eb5e76462f..fe118e0e3a 100644
--- a/src/link/MachO/Atom.zig
+++ b/src/link/MachO/Atom.zig
@@ -106,6 +106,7 @@ pub fn freeListEligible(self: Atom, macho_file: *MachO) bool {
}
pub fn getOutputSection(zld: *Zld, sect: macho.section_64) !?u8 {
+ const gpa = zld.gpa;
const segname = sect.segName();
const sectname = sect.sectName();
const res: ?u8 = blk: {
@@ -126,7 +127,9 @@ pub fn getOutputSection(zld: *Zld, sect: macho.section_64) !?u8 {
if (sect.isCode()) {
if (zld.text_section_index == null) {
- zld.text_section_index = try zld.initSection(
+ zld.text_section_index = try MachO.initSection(
+ gpa,
+ zld,
"__TEXT",
"__text",
.{
@@ -148,7 +151,9 @@ pub fn getOutputSection(zld: *Zld, sect: macho.section_64) !?u8 {
macho.S_8BYTE_LITERALS,
macho.S_16BYTE_LITERALS,
=> {
- break :blk zld.getSectionByName("__TEXT", "__const") orelse try zld.initSection(
+ break :blk zld.getSectionByName("__TEXT", "__const") orelse try MachO.initSection(
+ gpa,
+ zld,
"__TEXT",
"__const",
.{},
@@ -156,13 +161,17 @@ pub fn getOutputSection(zld: *Zld, sect: macho.section_64) !?u8 {
},
macho.S_CSTRING_LITERALS => {
if (mem.startsWith(u8, sectname, "__objc")) {
- break :blk zld.getSectionByName(segname, sectname) orelse try zld.initSection(
+ break :blk zld.getSectionByName(segname, sectname) orelse try MachO.initSection(
+ gpa,
+ zld,
segname,
sectname,
.{},
);
}
- break :blk zld.getSectionByName("__TEXT", "__cstring") orelse try zld.initSection(
+ break :blk zld.getSectionByName("__TEXT", "__cstring") orelse try MachO.initSection(
+ gpa,
+ zld,
"__TEXT",
"__cstring",
.{ .flags = macho.S_CSTRING_LITERALS },
@@ -171,7 +180,9 @@ pub fn getOutputSection(zld: *Zld, sect: macho.section_64) !?u8 {
macho.S_MOD_INIT_FUNC_POINTERS,
macho.S_MOD_TERM_FUNC_POINTERS,
=> {
- break :blk zld.getSectionByName("__DATA_CONST", sectname) orelse try zld.initSection(
+ break :blk zld.getSectionByName("__DATA_CONST", sectname) orelse try MachO.initSection(
+ gpa,
+ zld,
"__DATA_CONST",
sectname,
.{ .flags = sect.flags },
@@ -184,14 +195,19 @@ pub fn getOutputSection(zld: *Zld, sect: macho.section_64) !?u8 {
macho.S_THREAD_LOCAL_REGULAR,
macho.S_THREAD_LOCAL_ZEROFILL,
=> {
- break :blk zld.getSectionByName(segname, sectname) orelse try zld.initSection(
+ break :blk zld.getSectionByName(segname, sectname) orelse try MachO.initSection(
+ gpa,
+ zld,
segname,
sectname,
.{ .flags = sect.flags },
);
},
macho.S_COALESCED => {
- break :blk zld.getSectionByName(segname, sectname) orelse try zld.initSection(
+ break :blk zld.getSectionByName(segname, sectname) orelse try MachO.initSection(
+ gpa,
+ zld,
+
segname,
sectname,
.{},
@@ -205,7 +221,9 @@ pub fn getOutputSection(zld: *Zld, sect: macho.section_64) !?u8 {
mem.eql(u8, sectname, "__gosymtab") or
mem.eql(u8, sectname, "__gopclntab"))
{
- break :blk zld.getSectionByName("__TEXT", sectname) orelse try zld.initSection(
+ break :blk zld.getSectionByName("__TEXT", sectname) orelse try MachO.initSection(
+ gpa,
+ zld,
"__TEXT",
sectname,
.{},
@@ -218,20 +236,26 @@ pub fn getOutputSection(zld: *Zld, sect: macho.section_64) !?u8 {
mem.eql(u8, sectname, "__objc_classlist") or
mem.eql(u8, sectname, "__objc_imageinfo"))
{
- break :blk zld.getSectionByName("__DATA_CONST", sectname) orelse try zld.initSection(
+ break :blk zld.getSectionByName("__DATA_CONST", sectname) orelse try MachO.initSection(
+ gpa,
+ zld,
"__DATA_CONST",
sectname,
.{},
);
} else if (mem.eql(u8, sectname, "__data")) {
- break :blk zld.getSectionByName("__DATA", "__data") orelse try zld.initSection(
+ break :blk zld.getSectionByName("__DATA", "__data") orelse try MachO.initSection(
+ gpa,
+ zld,
"__DATA",
"__data",
.{},
);
}
}
- break :blk zld.getSectionByName(segname, sectname) orelse try zld.initSection(
+ break :blk zld.getSectionByName(segname, sectname) orelse try MachO.initSection(
+ gpa,
+ zld,
segname,
sectname,
.{},
diff --git a/src/link/MachO/Object.zig b/src/link/MachO/Object.zig
index c9f32aa4fd..2eee9f5787 100644
--- a/src/link/MachO/Object.zig
+++ b/src/link/MachO/Object.zig
@@ -685,11 +685,12 @@ fn parseEhFrameSection(self: *Object, zld: *Zld, object_id: u32) !void {
log.debug("parsing __TEXT,__eh_frame section", .{});
+ const gpa = zld.gpa;
+
if (zld.getSectionByName("__TEXT", "__eh_frame") == null) {
- _ = try zld.initSection("__TEXT", "__eh_frame", .{});
+ _ = try MachO.initSection(gpa, zld, "__TEXT", "__eh_frame", .{});
}
- const gpa = zld.gpa;
const cpu_arch = zld.options.target.cpu.arch;
try self.parseRelocs(gpa, sect_id);
const relocs = self.getRelocs(sect_id);
@@ -779,6 +780,8 @@ fn parseEhFrameSection(self: *Object, zld: *Zld, object_id: u32) !void {
}
fn parseUnwindInfo(self: *Object, zld: *Zld, object_id: u32) !void {
+ const gpa = zld.gpa;
+ const cpu_arch = zld.options.target.cpu.arch;
const sect_id = self.unwind_info_sect_id orelse {
// If it so happens that the object had `__eh_frame` section defined but no `__compact_unwind`,
// we will try fully synthesising unwind info records to somewhat match Apple ld's
@@ -786,7 +789,7 @@ fn parseUnwindInfo(self: *Object, zld: *Zld, object_id: u32) !void {
// we still create the output `__TEXT,__unwind_info` section.
if (self.hasEhFrameRecords()) {
if (zld.getSectionByName("__TEXT", "__unwind_info") == null) {
- _ = try zld.initSection("__TEXT", "__unwind_info", .{});
+ _ = try MachO.initSection(gpa, zld, "__TEXT", "__unwind_info", .{});
}
}
return;
@@ -794,11 +797,8 @@ fn parseUnwindInfo(self: *Object, zld: *Zld, object_id: u32) !void {
log.debug("parsing unwind info in {s}", .{self.name});
- const gpa = zld.gpa;
- const cpu_arch = zld.options.target.cpu.arch;
-
if (zld.getSectionByName("__TEXT", "__unwind_info") == null) {
- _ = try zld.initSection("__TEXT", "__unwind_info", .{});
+ _ = try MachO.initSection(gpa, zld, "__TEXT", "__unwind_info", .{});
}
const unwind_records = self.getUnwindRecords();
diff --git a/src/link/MachO/zld.zig b/src/link/MachO/zld.zig
index d4dd599d2d..5bfff40405 100644
--- a/src/link/MachO/zld.zig
+++ b/src/link/MachO/zld.zig
@@ -141,7 +141,7 @@ pub const Zld = struct {
sym.n_type = macho.N_SECT;
const sect_id = self.getSectionByName("__DATA", "__data") orelse
- try self.initSection("__DATA", "__data", .{});
+ try MachO.initSection(self.gpa, self, "__DATA", "__data", .{});
sym.n_sect = sect_id + 1;
self.dyld_private_atom_index = atom_index;
@@ -165,7 +165,7 @@ pub const Zld = struct {
const size = sym.n_value;
const alignment = (sym.n_desc >> 8) & 0x0f;
const sect_id = self.getSectionByName("__DATA", "__bss") orelse
- try self.initSection("__DATA", "__bss", .{ .flags = macho.S_ZEROFILL });
+ try MachO.initSection(gpa, self, "__DATA", "__bss", .{ .flags = macho.S_ZEROFILL });
sym.* = .{
.n_strx = sym.n_strx,
@@ -619,7 +619,7 @@ pub const Zld = struct {
if (self.got_table.lookup.contains(target)) return;
_ = try self.got_table.allocateEntry(self.gpa, target);
if (self.got_section_index == null) {
- self.got_section_index = try self.initSection("__DATA_CONST", "__got", .{
+ self.got_section_index = try MachO.initSection(self.gpa, self, "__DATA_CONST", "__got", .{
.flags = macho.S_NON_LAZY_SYMBOL_POINTERS,
});
}
@@ -629,7 +629,7 @@ pub const Zld = struct {
if (self.tlv_ptr_table.lookup.contains(target)) return;
_ = try self.tlv_ptr_table.allocateEntry(self.gpa, target);
if (self.tlv_ptr_section_index == null) {
- self.tlv_ptr_section_index = try self.initSection("__DATA", "__thread_ptrs", .{
+ self.tlv_ptr_section_index = try MachO.initSection(self.gpa, self, "__DATA", "__thread_ptrs", .{
.flags = macho.S_THREAD_LOCAL_VARIABLE_POINTERS,
});
}
@@ -639,18 +639,18 @@ pub const Zld = struct {
if (self.stubs_table.lookup.contains(target)) return;
_ = try self.stubs_table.allocateEntry(self.gpa, target);
if (self.stubs_section_index == null) {
- self.stubs_section_index = try self.initSection("__TEXT", "__stubs", .{
+ self.stubs_section_index = try MachO.initSection(self.gpa, self, "__TEXT", "__stubs", .{
.flags = macho.S_SYMBOL_STUBS |
macho.S_ATTR_PURE_INSTRUCTIONS |
macho.S_ATTR_SOME_INSTRUCTIONS,
.reserved2 = stubs.stubSize(self.options.target.cpu.arch),
});
- self.stub_helper_section_index = try self.initSection("__TEXT", "__stub_helper", .{
+ self.stub_helper_section_index = try MachO.initSection(self.gpa, self, "__TEXT", "__stub_helper", .{
.flags = macho.S_REGULAR |
macho.S_ATTR_PURE_INSTRUCTIONS |
macho.S_ATTR_SOME_INSTRUCTIONS,
});
- self.la_symbol_ptr_section_index = try self.initSection("__DATA", "__la_symbol_ptr", .{
+ self.la_symbol_ptr_section_index = try MachO.initSection(self.gpa, self, "__DATA", "__la_symbol_ptr", .{
.flags = macho.S_LAZY_SYMBOL_POINTERS,
});
}
@@ -1152,34 +1152,6 @@ pub const Zld = struct {
segment.vmsize = mem.alignForward(u64, segment.vmsize, page_size);
}
- const InitSectionOpts = struct {
- flags: u32 = macho.S_REGULAR,
- reserved1: u32 = 0,
- reserved2: u32 = 0,
- };
-
- pub fn initSection(
- self: *Zld,
- segname: []const u8,
- sectname: []const u8,
- opts: InitSectionOpts,
- ) !u8 {
- const gpa = self.gpa;
- log.debug("creating section '{s},{s}'", .{ segname, sectname });
- const index = @as(u8, @intCast(self.sections.slice().len));
- try self.sections.append(gpa, .{
- .segment_index = undefined, // Segments will be created automatically later down the pipeline
- .header = .{
- .sectname = makeStaticString(sectname),
- .segname = makeStaticString(segname),
- .flags = opts.flags,
- .reserved1 = opts.reserved1,
- .reserved2 = opts.reserved2,
- },
- });
- return index;
- }
-
fn writeSegmentHeaders(self: *Zld, writer: anytype) !void {
for (self.segments.items, 0..) |seg, i| {
const indexes = self.getSectionIndexes(@as(u8, @intCast(i)));