| author | |
| committer | |
| log | 06224c23b7ac3b4e31c6f63898da4107cbe918a8 |
| tree | b1a3c3d27efb171960096a968379b90ff494b7bb |
| parent | 67ea039426751bc8326c5835edca55ecf20dc66e |
12 files changed, 98 insertions(+), 69 deletions(-)
src/link/MachO.zig+29-18| ... | ... | @@ -2557,7 +2557,8 @@ fn writeAtoms(self: *MachO) !void { |
| 2557 | 2557 | if (atoms.items.len == 0) continue; |
| 2558 | 2558 | if (header.isZerofill()) continue; |
| 2559 | 2559 | |
| 2560 | const buffer = try gpa.alloc(u8, header.size); | |
| 2560 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 2561 | const buffer = try gpa.alloc(u8, size); | |
| 2561 | 2562 | defer gpa.free(buffer); |
| 2562 | 2563 | const padding_byte: u8 = if (header.isCode() and cpu_arch == .x86_64) 0xcc else 0; |
| 2563 | 2564 | @memset(buffer, padding_byte); |
| ... | ... | @@ -2565,14 +2566,15 @@ fn writeAtoms(self: *MachO) !void { |
| 2565 | 2566 | for (atoms.items) |atom_index| { |
| 2566 | 2567 | const atom = self.getAtom(atom_index).?; |
| 2567 | 2568 | assert(atom.flags.alive); |
| 2568 | const off = atom.value - header.addr; | |
| 2569 | const off = math.cast(usize, atom.value - header.addr) orelse return error.Overflow; | |
| 2569 | 2570 | const data = switch (atom.getFile(self)) { |
| 2570 | .object => |x| x.getAtomData(atom.*), | |
| 2571 | .object => |x| try x.getAtomData(atom.*), | |
| 2571 | 2572 | .zig_object => |x| try x.getAtomDataAlloc(self, arena.allocator(), atom.*), |
| 2572 | 2573 | else => unreachable, |
| 2573 | 2574 | }; |
| 2574 | @memcpy(buffer[off..][0..atom.size], data); | |
| 2575 | atom.resolveRelocs(self, buffer[off..][0..atom.size]) catch |err| switch (err) { | |
| 2575 | const atom_size = math.cast(usize, atom.size) orelse return error.Overflow; | |
| 2576 | @memcpy(buffer[off..][0..atom_size], data); | |
| 2577 | atom.resolveRelocs(self, buffer[off..][0..atom_size]) catch |err| switch (err) { | |
| 2576 | 2578 | error.ResolveFailed => has_resolve_error = true, |
| 2577 | 2579 | else => |e| return e, |
| 2578 | 2580 | }; |
| ... | ... | @@ -2602,7 +2604,8 @@ fn writeUnwindInfo(self: *MachO) !void { |
| 2602 | 2604 | |
| 2603 | 2605 | if (self.eh_frame_sect_index) |index| { |
| 2604 | 2606 | const header = self.sections.items(.header)[index]; |
| 2605 | const buffer = try gpa.alloc(u8, header.size); | |
| 2607 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 2608 | const buffer = try gpa.alloc(u8, size); | |
| 2606 | 2609 | defer gpa.free(buffer); |
| 2607 | 2610 | eh_frame.write(self, buffer); |
| 2608 | 2611 | try self.base.file.?.pwriteAll(buffer, header.offset); |
| ... | ... | @@ -2610,7 +2613,8 @@ fn writeUnwindInfo(self: *MachO) !void { |
| 2610 | 2613 | |
| 2611 | 2614 | if (self.unwind_info_sect_index) |index| { |
| 2612 | 2615 | const header = self.sections.items(.header)[index]; |
| 2613 | const buffer = try gpa.alloc(u8, header.size); | |
| 2616 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 2617 | const buffer = try gpa.alloc(u8, size); | |
| 2614 | 2618 | defer gpa.free(buffer); |
| 2615 | 2619 | try self.unwind_info.write(self, buffer); |
| 2616 | 2620 | try self.base.file.?.pwriteAll(buffer, header.offset); |
| ... | ... | @@ -2637,7 +2641,8 @@ fn writeSyntheticSections(self: *MachO) !void { |
| 2637 | 2641 | |
| 2638 | 2642 | if (self.got_sect_index) |sect_id| { |
| 2639 | 2643 | const header = self.sections.items(.header)[sect_id]; |
| 2640 | var buffer = try std.ArrayList(u8).initCapacity(gpa, header.size); | |
| 2644 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 2645 | var buffer = try std.ArrayList(u8).initCapacity(gpa, size); | |
| 2641 | 2646 | defer buffer.deinit(); |
| 2642 | 2647 | try self.got.write(self, buffer.writer()); |
| 2643 | 2648 | assert(buffer.items.len == header.size); |
| ... | ... | @@ -2646,7 +2651,8 @@ fn writeSyntheticSections(self: *MachO) !void { |
| 2646 | 2651 | |
| 2647 | 2652 | if (self.stubs_sect_index) |sect_id| { |
| 2648 | 2653 | const header = self.sections.items(.header)[sect_id]; |
| 2649 | var buffer = try std.ArrayList(u8).initCapacity(gpa, header.size); | |
| 2654 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 2655 | var buffer = try std.ArrayList(u8).initCapacity(gpa, size); | |
| 2650 | 2656 | defer buffer.deinit(); |
| 2651 | 2657 | try self.stubs.write(self, buffer.writer()); |
| 2652 | 2658 | assert(buffer.items.len == header.size); |
| ... | ... | @@ -2655,7 +2661,8 @@ fn writeSyntheticSections(self: *MachO) !void { |
| 2655 | 2661 | |
| 2656 | 2662 | if (self.stubs_helper_sect_index) |sect_id| { |
| 2657 | 2663 | const header = self.sections.items(.header)[sect_id]; |
| 2658 | var buffer = try std.ArrayList(u8).initCapacity(gpa, header.size); | |
| 2664 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 2665 | var buffer = try std.ArrayList(u8).initCapacity(gpa, size); | |
| 2659 | 2666 | defer buffer.deinit(); |
| 2660 | 2667 | try self.stubs_helper.write(self, buffer.writer()); |
| 2661 | 2668 | assert(buffer.items.len == header.size); |
| ... | ... | @@ -2664,7 +2671,8 @@ fn writeSyntheticSections(self: *MachO) !void { |
| 2664 | 2671 | |
| 2665 | 2672 | if (self.la_symbol_ptr_sect_index) |sect_id| { |
| 2666 | 2673 | const header = self.sections.items(.header)[sect_id]; |
| 2667 | var buffer = try std.ArrayList(u8).initCapacity(gpa, header.size); | |
| 2674 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 2675 | var buffer = try std.ArrayList(u8).initCapacity(gpa, size); | |
| 2668 | 2676 | defer buffer.deinit(); |
| 2669 | 2677 | try self.la_symbol_ptr.write(self, buffer.writer()); |
| 2670 | 2678 | assert(buffer.items.len == header.size); |
| ... | ... | @@ -2673,7 +2681,8 @@ fn writeSyntheticSections(self: *MachO) !void { |
| 2673 | 2681 | |
| 2674 | 2682 | if (self.tlv_ptr_sect_index) |sect_id| { |
| 2675 | 2683 | const header = self.sections.items(.header)[sect_id]; |
| 2676 | var buffer = try std.ArrayList(u8).initCapacity(gpa, header.size); | |
| 2684 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 2685 | var buffer = try std.ArrayList(u8).initCapacity(gpa, size); | |
| 2677 | 2686 | defer buffer.deinit(); |
| 2678 | 2687 | try self.tlv_ptr.write(self, buffer.writer()); |
| 2679 | 2688 | assert(buffer.items.len == header.size); |
| ... | ... | @@ -2682,7 +2691,8 @@ fn writeSyntheticSections(self: *MachO) !void { |
| 2682 | 2691 | |
| 2683 | 2692 | if (self.objc_stubs_sect_index) |sect_id| { |
| 2684 | 2693 | const header = self.sections.items(.header)[sect_id]; |
| 2685 | var buffer = try std.ArrayList(u8).initCapacity(gpa, header.size); | |
| 2694 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 2695 | var buffer = try std.ArrayList(u8).initCapacity(gpa, size); | |
| 2686 | 2696 | defer buffer.deinit(); |
| 2687 | 2697 | try self.objc_stubs.write(self, buffer.writer()); |
| 2688 | 2698 | assert(buffer.items.len == header.size); |
| ... | ... | @@ -2876,10 +2886,10 @@ pub fn writeSymtab(self: *MachO, off: u32) !u32 { |
| 2876 | 2886 | zo.writeSymtab(self); |
| 2877 | 2887 | } |
| 2878 | 2888 | for (self.objects.items) |index| { |
| 2879 | self.getFile(index).?.writeSymtab(self); | |
| 2889 | try self.getFile(index).?.writeSymtab(self); | |
| 2880 | 2890 | } |
| 2881 | 2891 | for (self.dylibs.items) |index| { |
| 2882 | self.getFile(index).?.writeSymtab(self); | |
| 2892 | try self.getFile(index).?.writeSymtab(self); | |
| 2883 | 2893 | } |
| 2884 | 2894 | if (self.getInternalObject()) |internal| { |
| 2885 | 2895 | internal.writeSymtab(self); |
| ... | ... | @@ -2916,7 +2926,7 @@ pub fn writeStrtab(self: *MachO, off: u32) !u32 { |
| 2916 | 2926 | return off + cmd.strsize; |
| 2917 | 2927 | } |
| 2918 | 2928 | |
| 2919 | fn writeLoadCommands(self: *MachO) !struct { usize, usize, usize } { | |
| 2929 | fn writeLoadCommands(self: *MachO) !struct { usize, usize, u64 } { | |
| 2920 | 2930 | const gpa = self.base.comp.gpa; |
| 2921 | 2931 | const needed_size = load_commands.calcLoadCommandsSize(self, false); |
| 2922 | 2932 | const buffer = try gpa.alloc(u8, needed_size); |
| ... | ... | @@ -3075,7 +3085,7 @@ fn writeHeader(self: *MachO, ncmds: usize, sizeofcmds: usize) !void { |
| 3075 | 3085 | try self.base.file.?.pwriteAll(mem.asBytes(&header), 0); |
| 3076 | 3086 | } |
| 3077 | 3087 | |
| 3078 | fn writeUuid(self: *MachO, uuid_cmd_offset: usize, has_codesig: bool) !void { | |
| 3088 | fn writeUuid(self: *MachO, uuid_cmd_offset: u64, has_codesig: bool) !void { | |
| 3079 | 3089 | const file_size = if (!has_codesig) blk: { |
| 3080 | 3090 | const seg = self.getLinkeditSegment(); |
| 3081 | 3091 | break :blk seg.fileoff + seg.filesize; |
| ... | ... | @@ -3273,7 +3283,8 @@ fn copyRangeAllZeroOut(self: *MachO, old_offset: u64, new_offset: u64, size: u64 |
| 3273 | 3283 | const file = self.base.file.?; |
| 3274 | 3284 | const amt = try file.copyRangeAll(old_offset, file, new_offset, size); |
| 3275 | 3285 | if (amt != size) return error.InputOutput; |
| 3276 | const zeroes = try gpa.alloc(u8, size); | |
| 3286 | const size_u = math.cast(usize, size) orelse return error.Overflow; | |
| 3287 | const zeroes = try gpa.alloc(u8, size_u); | |
| 3277 | 3288 | defer gpa.free(zeroes); |
| 3278 | 3289 | @memset(zeroes, 0); |
| 3279 | 3290 | try file.pwriteAll(zeroes, old_offset); |
src/link/MachO/Atom.zig+1-1| ... | ... | @@ -579,7 +579,7 @@ fn resolveRelocInner( |
| 579 | 579 | writer: anytype, |
| 580 | 580 | ) ResolveError!void { |
| 581 | 581 | const cpu_arch = macho_file.getTarget().cpu.arch; |
| 582 | const rel_offset = rel.offset - self.off; | |
| 582 | const rel_offset = math.cast(usize, rel.offset - self.off) orelse return error.Overflow; | |
| 583 | 583 | const seg_id = macho_file.sections.items(.segment_id)[self.out_n_sect]; |
| 584 | 584 | const seg = macho_file.segments.items[seg_id]; |
| 585 | 585 | const P = @as(i64, @intCast(self.value)) + @as(i64, @intCast(rel_offset)); |
src/link/MachO/DwarfInfo.zig+13-10| ... | ... | @@ -20,7 +20,7 @@ pub fn deinit(dw: *DwarfInfo, allocator: Allocator) void { |
| 20 | 20 | dw.compile_units.deinit(allocator); |
| 21 | 21 | } |
| 22 | 22 | |
| 23 | fn getString(dw: DwarfInfo, off: u64) [:0]const u8 { | |
| 23 | fn getString(dw: DwarfInfo, off: usize) [:0]const u8 { | |
| 24 | 24 | assert(off < dw.debug_str.len); |
| 25 | 25 | return mem.sliceTo(@as([*:0]const u8, @ptrCast(dw.debug_str.ptr + off)), 0); |
| 26 | 26 | } |
| ... | ... | @@ -144,9 +144,9 @@ fn parseDie( |
| 144 | 144 | try cu.diePtr(die).values.ensureTotalCapacityPrecise(allocator, decl.attrs.values().len); |
| 145 | 145 | |
| 146 | 146 | for (decl.attrs.values()) |attr| { |
| 147 | const start = creader.bytes_read; | |
| 147 | const start = std.math.cast(usize, creader.bytes_read) orelse return error.Overflow; | |
| 148 | 148 | try advanceByFormSize(cu, attr.form, creader); |
| 149 | const end = creader.bytes_read; | |
| 149 | const end = std.math.cast(usize, creader.bytes_read) orelse return error.Overflow; | |
| 150 | 150 | cu.diePtr(die).values.appendAssumeCapacity(data[start..end]); |
| 151 | 151 | } |
| 152 | 152 | |
| ... | ... | @@ -184,14 +184,16 @@ fn advanceByFormSize(cu: *CompileUnit, form: Form, creader: anytype) !void { |
| 184 | 184 | dwarf.FORM.block => try leb.readULEB128(u64, reader), |
| 185 | 185 | else => unreachable, |
| 186 | 186 | }; |
| 187 | for (0..len) |_| { | |
| 187 | var i: u64 = 0; | |
| 188 | while (i < len) : (i += 1) { | |
| 188 | 189 | _ = try reader.readByte(); |
| 189 | 190 | } |
| 190 | 191 | }, |
| 191 | 192 | |
| 192 | 193 | dwarf.FORM.exprloc => { |
| 193 | 194 | const len = try leb.readULEB128(u64, reader); |
| 194 | for (0..len) |_| { | |
| 195 | var i: u64 = 0; | |
| 196 | while (i < len) : (i += 1) { | |
| 195 | 197 | _ = try reader.readByte(); |
| 196 | 198 | } |
| 197 | 199 | }, |
| ... | ... | @@ -292,7 +294,7 @@ pub const CompileUnitHeader = struct { |
| 292 | 294 | |
| 293 | 295 | pub const CompileUnit = struct { |
| 294 | 296 | header: CompileUnitHeader, |
| 295 | pos: usize, | |
| 297 | pos: u64, | |
| 296 | 298 | dies: std.ArrayListUnmanaged(Die) = .{}, |
| 297 | 299 | children: std.ArrayListUnmanaged(Die.Index) = .{}, |
| 298 | 300 | |
| ... | ... | @@ -314,14 +316,14 @@ pub const CompileUnit = struct { |
| 314 | 316 | return &cu.dies.items[index]; |
| 315 | 317 | } |
| 316 | 318 | |
| 317 | pub fn getCompileDir(cu: CompileUnit, ctx: DwarfInfo) ?[:0]const u8 { | |
| 319 | pub fn getCompileDir(cu: CompileUnit, ctx: DwarfInfo) error{Overflow}!?[:0]const u8 { | |
| 318 | 320 | assert(cu.dies.items.len > 0); |
| 319 | 321 | const die = cu.dies.items[0]; |
| 320 | 322 | const res = die.find(dwarf.AT.comp_dir, cu, ctx) orelse return null; |
| 321 | 323 | return res.getString(cu.header.format, ctx); |
| 322 | 324 | } |
| 323 | 325 | |
| 324 | pub fn getSourceFile(cu: CompileUnit, ctx: DwarfInfo) ?[:0]const u8 { | |
| 326 | pub fn getSourceFile(cu: CompileUnit, ctx: DwarfInfo) error{Overflow}!?[:0]const u8 { | |
| 325 | 327 | assert(cu.dies.items.len > 0); |
| 326 | 328 | const die = cu.dies.items[0]; |
| 327 | 329 | const res = die.find(dwarf.AT.name, cu, ctx) orelse return null; |
| ... | ... | @@ -370,7 +372,7 @@ pub const DieValue = struct { |
| 370 | 372 | }; |
| 371 | 373 | } |
| 372 | 374 | |
| 373 | pub fn getString(value: DieValue, format: Format, ctx: DwarfInfo) ?[:0]const u8 { | |
| 375 | pub fn getString(value: DieValue, format: Format, ctx: DwarfInfo) error{Overflow}!?[:0]const u8 { | |
| 374 | 376 | switch (value.attr.form) { |
| 375 | 377 | dwarf.FORM.string => { |
| 376 | 378 | return mem.sliceTo(@as([*:0]const u8, @ptrCast(value.bytes.ptr)), 0); |
| ... | ... | @@ -380,7 +382,8 @@ pub const DieValue = struct { |
| 380 | 382 | .dwarf64 => mem.readInt(u64, value.bytes[0..8], .little), |
| 381 | 383 | .dwarf32 => mem.readInt(u32, value.bytes[0..4], .little), |
| 382 | 384 | }; |
| 383 | return ctx.getString(off); | |
| 385 | const off_u = std.math.cast(usize, off) orelse return error.Overflow; | |
| 386 | return ctx.getString(off_u); | |
| 384 | 387 | }, |
| 385 | 388 | else => return null, |
| 386 | 389 | } |
src/link/MachO/Dylib.zig+2-2| ... | ... | @@ -139,7 +139,7 @@ const TrieIterator = struct { |
| 139 | 139 | var creader = std.io.countingReader(stream.reader()); |
| 140 | 140 | const reader = creader.reader(); |
| 141 | 141 | const value = try std.leb.readULEB128(u64, reader); |
| 142 | it.pos += creader.bytes_read; | |
| 142 | it.pos += math.cast(usize, creader.bytes_read) orelse return error.Overflow; | |
| 143 | 143 | return value; |
| 144 | 144 | } |
| 145 | 145 | |
| ... | ... | @@ -212,7 +212,7 @@ fn parseTrieNode( |
| 212 | 212 | const off = try it.readULEB128(); |
| 213 | 213 | const prefix_label = try std.fmt.allocPrint(arena, "{s}{s}", .{ prefix, label }); |
| 214 | 214 | const curr = it.pos; |
| 215 | it.pos = off; | |
| 215 | it.pos = math.cast(usize, off) orelse return error.Overflow; | |
| 216 | 216 | try self.parseTrieNode(it, allocator, arena, prefix_label); |
| 217 | 217 | it.pos = curr; |
| 218 | 218 | } |
src/link/MachO/Object.zig+25-21| ... | ... | @@ -632,7 +632,7 @@ fn initEhFrameRecords(self: *Object, sect_id: u8, macho_file: *MachO) !void { |
| 632 | 632 | const sect = slice.items(.header)[sect_id]; |
| 633 | 633 | const relocs = slice.items(.relocs)[sect_id]; |
| 634 | 634 | |
| 635 | const data = self.getSectionData(sect_id); | |
| 635 | const data = try self.getSectionData(sect_id); | |
| 636 | 636 | try self.eh_frame_data.ensureTotalCapacityPrecise(gpa, data.len); |
| 637 | 637 | self.eh_frame_data.appendSliceAssumeCapacity(data); |
| 638 | 638 | |
| ... | ... | @@ -733,7 +733,7 @@ fn initUnwindRecords(self: *Object, sect_id: u8, macho_file: *MachO) !void { |
| 733 | 733 | }; |
| 734 | 734 | |
| 735 | 735 | const gpa = macho_file.base.comp.gpa; |
| 736 | const data = self.getSectionData(sect_id); | |
| 736 | const data = try self.getSectionData(sect_id); | |
| 737 | 737 | const nrecs = @divExact(data.len, @sizeOf(macho.compact_unwind_entry)); |
| 738 | 738 | const recs = @as([*]align(1) const macho.compact_unwind_entry, @ptrCast(data.ptr))[0..nrecs]; |
| 739 | 739 | const sym_lookup = SymbolLookup{ .ctx = self }; |
| ... | ... | @@ -974,9 +974,9 @@ fn initDwarfInfo(self: *Object, macho_file: *MachO) !void { |
| 974 | 974 | if (debug_info_index == null or debug_abbrev_index == null) return; |
| 975 | 975 | |
| 976 | 976 | var dwarf_info = DwarfInfo{ |
| 977 | .debug_info = self.getSectionData(@intCast(debug_info_index.?)), | |
| 978 | .debug_abbrev = self.getSectionData(@intCast(debug_abbrev_index.?)), | |
| 979 | .debug_str = if (debug_str_index) |index| self.getSectionData(@intCast(index)) else "", | |
| 977 | .debug_info = try self.getSectionData(@intCast(debug_info_index.?)), | |
| 978 | .debug_abbrev = try self.getSectionData(@intCast(debug_abbrev_index.?)), | |
| 979 | .debug_str = if (debug_str_index) |index| try self.getSectionData(@intCast(index)) else "", | |
| 980 | 980 | }; |
| 981 | 981 | dwarf_info.init(gpa) catch { |
| 982 | 982 | try macho_file.reportParseError2(self.index, "invalid __DWARF info found", .{}); |
| ... | ... | @@ -1203,15 +1203,15 @@ pub fn calcSymtabSize(self: *Object, macho_file: *MachO) !void { |
| 1203 | 1203 | } |
| 1204 | 1204 | |
| 1205 | 1205 | if (macho_file.base.comp.config.debug_format != .strip and self.hasDebugInfo()) |
| 1206 | self.calcStabsSize(macho_file); | |
| 1206 | try self.calcStabsSize(macho_file); | |
| 1207 | 1207 | } |
| 1208 | 1208 | |
| 1209 | pub fn calcStabsSize(self: *Object, macho_file: *MachO) void { | |
| 1209 | pub fn calcStabsSize(self: *Object, macho_file: *MachO) error{Overflow}!void { | |
| 1210 | 1210 | if (self.dwarf_info) |dw| { |
| 1211 | 1211 | // TODO handle multiple CUs |
| 1212 | 1212 | const cu = dw.compile_units.items[0]; |
| 1213 | const comp_dir = cu.getCompileDir(dw) orelse return; | |
| 1214 | const tu_name = cu.getSourceFile(dw) orelse return; | |
| 1213 | const comp_dir = try cu.getCompileDir(dw) orelse return; | |
| 1214 | const tu_name = try cu.getSourceFile(dw) orelse return; | |
| 1215 | 1215 | |
| 1216 | 1216 | self.output_symtab_ctx.nstabs += 4; // N_SO, N_SO, N_OSO, N_SO |
| 1217 | 1217 | self.output_symtab_ctx.strsize += @as(u32, @intCast(comp_dir.len + 1)); // comp_dir |
| ... | ... | @@ -1266,7 +1266,7 @@ pub fn calcStabsSize(self: *Object, macho_file: *MachO) void { |
| 1266 | 1266 | } |
| 1267 | 1267 | } |
| 1268 | 1268 | |
| 1269 | pub fn writeSymtab(self: Object, macho_file: *MachO) void { | |
| 1269 | pub fn writeSymtab(self: Object, macho_file: *MachO) error{Overflow}!void { | |
| 1270 | 1270 | const tracy = trace(@src()); |
| 1271 | 1271 | defer tracy.end(); |
| 1272 | 1272 | |
| ... | ... | @@ -1284,10 +1284,10 @@ pub fn writeSymtab(self: Object, macho_file: *MachO) void { |
| 1284 | 1284 | } |
| 1285 | 1285 | |
| 1286 | 1286 | if (macho_file.base.comp.config.debug_format != .strip and self.hasDebugInfo()) |
| 1287 | self.writeStabs(macho_file); | |
| 1287 | try self.writeStabs(macho_file); | |
| 1288 | 1288 | } |
| 1289 | 1289 | |
| 1290 | pub fn writeStabs(self: *const Object, macho_file: *MachO) void { | |
| 1290 | pub fn writeStabs(self: *const Object, macho_file: *MachO) error{Overflow}!void { | |
| 1291 | 1291 | const writeFuncStab = struct { |
| 1292 | 1292 | inline fn writeFuncStab( |
| 1293 | 1293 | n_strx: u32, |
| ... | ... | @@ -1333,8 +1333,8 @@ pub fn writeStabs(self: *const Object, macho_file: *MachO) void { |
| 1333 | 1333 | if (self.dwarf_info) |dw| { |
| 1334 | 1334 | // TODO handle multiple CUs |
| 1335 | 1335 | const cu = dw.compile_units.items[0]; |
| 1336 | const comp_dir = cu.getCompileDir(dw) orelse return; | |
| 1337 | const tu_name = cu.getSourceFile(dw) orelse return; | |
| 1336 | const comp_dir = try cu.getCompileDir(dw) orelse return; | |
| 1337 | const tu_name = try cu.getSourceFile(dw) orelse return; | |
| 1338 | 1338 | |
| 1339 | 1339 | // Open scope |
| 1340 | 1340 | // N_SO comp_dir |
| ... | ... | @@ -1540,16 +1540,20 @@ fn getLoadCommand(self: Object, lc: macho.LC) ?LoadCommandIterator.LoadCommand { |
| 1540 | 1540 | } else return null; |
| 1541 | 1541 | } |
| 1542 | 1542 | |
| 1543 | pub fn getSectionData(self: *const Object, index: u32) []const u8 { | |
| 1543 | pub fn getSectionData(self: *const Object, index: u32) error{Overflow}![]const u8 { | |
| 1544 | 1544 | const slice = self.sections.slice(); |
| 1545 | 1545 | assert(index < slice.items(.header).len); |
| 1546 | 1546 | const sect = slice.items(.header)[index]; |
| 1547 | return self.data[sect.offset..][0..sect.size]; | |
| 1547 | const off = math.cast(usize, sect.offset) orelse return error.Overflow; | |
| 1548 | const size = math.cast(usize, sect.size) orelse return error.Overflow; | |
| 1549 | return self.data[off..][0..size]; | |
| 1548 | 1550 | } |
| 1549 | 1551 | |
| 1550 | pub fn getAtomData(self: *const Object, atom: Atom) []const u8 { | |
| 1551 | const data = self.getSectionData(atom.n_sect); | |
| 1552 | return data[atom.off..][0..atom.size]; | |
| 1552 | pub fn getAtomData(self: *const Object, atom: Atom) error{Overflow}![]const u8 { | |
| 1553 | const data = try self.getSectionData(atom.n_sect); | |
| 1554 | const off = math.cast(usize, atom.off) orelse return error.Overflow; | |
| 1555 | const size = math.cast(usize, atom.size) orelse return error.Overflow; | |
| 1556 | return data[off..][0..size]; | |
| 1553 | 1557 | } |
| 1554 | 1558 | |
| 1555 | 1559 | pub fn getAtomRelocs(self: *const Object, atom: Atom) []const Relocation { |
| ... | ... | @@ -1821,7 +1825,7 @@ const x86_64 = struct { |
| 1821 | 1825 | [*]align(1) const macho.relocation_info, |
| 1822 | 1826 | @ptrCast(self.data.ptr + sect.reloff), |
| 1823 | 1827 | )[0..sect.nreloc]; |
| 1824 | const code = self.getSectionData(@intCast(n_sect)); | |
| 1828 | const code = try self.getSectionData(@intCast(n_sect)); | |
| 1825 | 1829 | |
| 1826 | 1830 | try out.ensureTotalCapacityPrecise(gpa, relocs.len); |
| 1827 | 1831 | |
| ... | ... | @@ -1977,7 +1981,7 @@ const aarch64 = struct { |
| 1977 | 1981 | [*]align(1) const macho.relocation_info, |
| 1978 | 1982 | @ptrCast(self.data.ptr + sect.reloff), |
| 1979 | 1983 | )[0..sect.nreloc]; |
| 1980 | const code = self.getSectionData(@intCast(n_sect)); | |
| 1984 | const code = try self.getSectionData(@intCast(n_sect)); | |
| 1981 | 1985 | |
| 1982 | 1986 | try out.ensureTotalCapacityPrecise(gpa, relocs.len); |
| 1983 | 1987 |
src/link/MachO/UnwindInfo.zig+4-2| ... | ... | @@ -333,13 +333,15 @@ pub fn write(info: UnwindInfo, macho_file: *MachO, buffer: []u8) !void { |
| 333 | 333 | try page.write(info, macho_file, writer); |
| 334 | 334 | const nwritten = cwriter.bytes_written - start; |
| 335 | 335 | if (nwritten < second_level_page_bytes) { |
| 336 | try writer.writeByteNTimes(0, second_level_page_bytes - nwritten); | |
| 336 | const padding = math.cast(usize, second_level_page_bytes - nwritten) orelse return error.Overflow; | |
| 337 | try writer.writeByteNTimes(0, padding); | |
| 337 | 338 | } |
| 338 | 339 | } |
| 339 | 340 | |
| 340 | 341 | const padding = buffer.len - cwriter.bytes_written; |
| 341 | 342 | if (padding > 0) { |
| 342 | @memset(buffer[cwriter.bytes_written..], 0); | |
| 343 | const off = math.cast(usize, cwriter.bytes_written) orelse return error.Overflow; | |
| 344 | @memset(buffer[off..], 0); | |
| 343 | 345 | } |
| 344 | 346 | } |
| 345 | 347 |
src/link/MachO/ZigObject.zig+2-1| ... | ... | @@ -154,7 +154,8 @@ pub fn getAtomDataAlloc( |
| 154 | 154 | return data; |
| 155 | 155 | }, |
| 156 | 156 | macho.S_THREAD_LOCAL_VARIABLES => { |
| 157 | const data = try allocator.alloc(u8, atom.size); | |
| 157 | const size = std.math.cast(usize, atom.size) orelse return error.Overflow; | |
| 158 | const data = try allocator.alloc(u8, size); | |
| 158 | 159 | @memset(data, 0); |
| 159 | 160 | return data; |
| 160 | 161 | }, |
src/link/MachO/dyld_info/Rebase.zig+1-1| ... | ... | @@ -181,7 +181,7 @@ fn rebaseTimesSkip(count: usize, skip: u64, writer: anytype) !void { |
| 181 | 181 | |
| 182 | 182 | fn addAddr(addr: u64, writer: anytype) !void { |
| 183 | 183 | log.debug(">>> add: {x}", .{addr}); |
| 184 | if (std.mem.isAligned(addr, @sizeOf(u64))) { | |
| 184 | if (std.mem.isAlignedGeneric(u64, addr, @sizeOf(u64))) { | |
| 185 | 185 | const imm = @divExact(addr, @sizeOf(u64)); |
| 186 | 186 | if (imm <= 0xf) { |
| 187 | 187 | try writer.writeByte(macho.REBASE_OPCODE_ADD_ADDR_IMM_SCALED | @as(u4, @truncate(imm))); |
src/link/MachO/dyld_info/bind.zig+1-1| ... | ... | @@ -448,7 +448,7 @@ fn doBind(writer: anytype) !void { |
| 448 | 448 | |
| 449 | 449 | fn doBindAddAddr(addr: u64, writer: anytype) !void { |
| 450 | 450 | log.debug(">>> bind with add: {x}", .{addr}); |
| 451 | if (std.mem.isAligned(addr, @sizeOf(u64))) { | |
| 451 | if (std.mem.isAlignedGeneric(u64, addr, @sizeOf(u64))) { | |
| 452 | 452 | const imm = @divExact(addr, @sizeOf(u64)); |
| 453 | 453 | if (imm <= 0xf) { |
| 454 | 454 | try writer.writeByte( |
src/link/MachO/file.zig+1-1| ... | ... | @@ -90,7 +90,7 @@ pub const File = union(enum) { |
| 90 | 90 | }; |
| 91 | 91 | } |
| 92 | 92 | |
| 93 | pub fn writeSymtab(file: File, macho_file: *MachO) void { | |
| 93 | pub fn writeSymtab(file: File, macho_file: *MachO) !void { | |
| 94 | 94 | return switch (file) { |
| 95 | 95 | inline else => |x| x.writeSymtab(macho_file), |
| 96 | 96 | }; |
src/link/MachO/hasher.zig+9-5| ... | ... | @@ -14,9 +14,13 @@ pub fn ParallelHasher(comptime Hasher: type) type { |
| 14 | 14 | |
| 15 | 15 | var wg: WaitGroup = .{}; |
| 16 | 16 | |
| 17 | const file_size = opts.max_file_size orelse try file.getEndPos(); | |
| 17 | const file_size = blk: { | |
| 18 | const file_size = opts.max_file_size orelse try file.getEndPos(); | |
| 19 | break :blk std.math.cast(usize, file_size) orelse return error.Overflow; | |
| 20 | }; | |
| 21 | const chunk_size = std.math.cast(usize, opts.chunk_size) orelse return error.Overflow; | |
| 18 | 22 | |
| 19 | const buffer = try self.allocator.alloc(u8, opts.chunk_size * out.len); | |
| 23 | const buffer = try self.allocator.alloc(u8, chunk_size * out.len); | |
| 20 | 24 | defer self.allocator.free(buffer); |
| 21 | 25 | |
| 22 | 26 | const results = try self.allocator.alloc(fs.File.PReadError!usize, out.len); |
| ... | ... | @@ -27,11 +31,11 @@ pub fn ParallelHasher(comptime Hasher: type) type { |
| 27 | 31 | defer wg.wait(); |
| 28 | 32 | |
| 29 | 33 | for (out, results, 0..) |*out_buf, *result, i| { |
| 30 | const fstart = i * opts.chunk_size; | |
| 31 | const fsize = if (fstart + opts.chunk_size > file_size) | |
| 34 | const fstart = i * chunk_size; | |
| 35 | const fsize = if (fstart + chunk_size > file_size) | |
| 32 | 36 | file_size - fstart |
| 33 | 37 | else |
| 34 | opts.chunk_size; | |
| 38 | chunk_size; | |
| 35 | 39 | wg.start(); |
| 36 | 40 | try self.thread_pool.spawn(worker, .{ |
| 37 | 41 | file, |
src/link/MachO/relocatable.zig+10-6| ... | ... | @@ -262,7 +262,8 @@ fn writeAtoms(macho_file: *MachO) !void { |
| 262 | 262 | if (atoms.items.len == 0) continue; |
| 263 | 263 | if (header.isZerofill()) continue; |
| 264 | 264 | |
| 265 | const code = try gpa.alloc(u8, header.size); | |
| 265 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 266 | const code = try gpa.alloc(u8, size); | |
| 266 | 267 | defer gpa.free(code); |
| 267 | 268 | const padding_byte: u8 = if (header.isCode() and cpu_arch == .x86_64) 0xcc else 0; |
| 268 | 269 | @memset(code, padding_byte); |
| ... | ... | @@ -273,9 +274,11 @@ fn writeAtoms(macho_file: *MachO) !void { |
| 273 | 274 | for (atoms.items) |atom_index| { |
| 274 | 275 | const atom = macho_file.getAtom(atom_index).?; |
| 275 | 276 | assert(atom.flags.alive); |
| 276 | const off = atom.value - header.addr; | |
| 277 | @memcpy(code[off..][0..atom.size], atom.getFile(macho_file).object.getAtomData(atom.*)); | |
| 278 | try atom.writeRelocs(macho_file, code[off..][0..atom.size], &relocs); | |
| 277 | const off = math.cast(usize, atom.value - header.addr) orelse return error.Overflow; | |
| 278 | const atom_size = math.cast(usize, atom.size) orelse return error.Overflow; | |
| 279 | const atom_data = try atom.getFile(macho_file).object.getAtomData(atom.*); | |
| 280 | @memcpy(code[off..][0..atom_size], atom_data); | |
| 281 | try atom.writeRelocs(macho_file, code[off..][0..atom_size], &relocs); | |
| 279 | 282 | } |
| 280 | 283 | |
| 281 | 284 | assert(relocs.items.len == header.nreloc); |
| ... | ... | @@ -293,7 +296,7 @@ fn writeCompactUnwind(macho_file: *MachO) !void { |
| 293 | 296 | const gpa = macho_file.base.comp.gpa; |
| 294 | 297 | const header = macho_file.sections.items(.header)[sect_index]; |
| 295 | 298 | |
| 296 | const nrecs = @divExact(header.size, @sizeOf(macho.compact_unwind_entry)); | |
| 299 | const nrecs = math.cast(usize, @divExact(header.size, @sizeOf(macho.compact_unwind_entry))) orelse return error.Overflow; | |
| 297 | 300 | var entries = try std.ArrayList(macho.compact_unwind_entry).initCapacity(gpa, nrecs); |
| 298 | 301 | defer entries.deinit(); |
| 299 | 302 | |
| ... | ... | @@ -379,8 +382,9 @@ fn writeEhFrame(macho_file: *MachO) !void { |
| 379 | 382 | const sect_index = macho_file.eh_frame_sect_index orelse return; |
| 380 | 383 | const gpa = macho_file.base.comp.gpa; |
| 381 | 384 | const header = macho_file.sections.items(.header)[sect_index]; |
| 385 | const size = math.cast(usize, header.size) orelse return error.Overflow; | |
| 382 | 386 | |
| 383 | const code = try gpa.alloc(u8, header.size); | |
| 387 | const code = try gpa.alloc(u8, size); | |
| 384 | 388 | defer gpa.free(code); |
| 385 | 389 | |
| 386 | 390 | var relocs = try std.ArrayList(macho.relocation_info).initCapacity(gpa, header.nreloc); |