| author | |
| committer | |
| log | de0f7fcf526312088e4b373c6ed7436427080087 |
| tree | 9793bf83f7c1eaf893754af273b8fbd6ea772796 |
| parent | 12f3a7c3c202475c67b639c369829a0390cfb0f8 |
3 files changed, 21 insertions(+), 60 deletions(-)
src/link/Elf.zig+17-8| ... | @@ -765,6 +765,7 @@ pub fn loadInput(self: *Elf, input: link.Input) !void { | ... | @@ -765,6 +765,7 @@ pub fn loadInput(self: *Elf, input: link.Input) !void { |
| 765 | const target = self.getTarget(); | 765 | const target = self.getTarget(); |
| 766 | const debug_fmt_strip = comp.config.debug_format == .strip; | 766 | const debug_fmt_strip = comp.config.debug_format == .strip; |
| 767 | const default_sym_version = self.default_sym_version; | 767 | const default_sym_version = self.default_sym_version; |
| 768 | const is_static_lib = self.base.isStaticLib(); | ||
| 768 | 769 | ||
| 769 | if (comp.verbose_link) { | 770 | if (comp.verbose_link) { |
| 770 | const argv = &self.dump_argv_list; | 771 | const argv = &self.dump_argv_list; |
| ... | @@ -780,7 +781,7 @@ pub fn loadInput(self: *Elf, input: link.Input) !void { | ... | @@ -780,7 +781,7 @@ pub fn loadInput(self: *Elf, input: link.Input) !void { |
| 780 | .res => unreachable, | 781 | .res => unreachable, |
| 781 | .dso_exact => @panic("TODO"), | 782 | .dso_exact => @panic("TODO"), |
| 782 | .object => |obj| try parseObject(self, obj), | 783 | .object => |obj| try parseObject(self, obj), |
| 783 | .archive => |obj| try parseArchive(gpa, diags, &self.file_handles, &self.files, &self.first_eflags, target, debug_fmt_strip, default_sym_version, &self.objects, obj), | 784 | .archive => |obj| try parseArchive(gpa, diags, &self.file_handles, &self.files, &self.first_eflags, target, debug_fmt_strip, default_sym_version, &self.objects, obj, is_static_lib), |
| 784 | .dso => |dso| try parseDso(gpa, diags, dso, &self.shared_objects, &self.files, target), | 785 | .dso => |dso| try parseDso(gpa, diags, dso, &self.shared_objects, &self.files, target), |
| 785 | } | 786 | } |
| 786 | } | 787 | } |
| ... | @@ -823,17 +824,17 @@ pub fn flushModule(self: *Elf, arena: Allocator, tid: Zcu.PerThread.Id, prog_nod | ... | @@ -823,17 +824,17 @@ pub fn flushModule(self: *Elf, arena: Allocator, tid: Zcu.PerThread.Id, prog_nod |
| 823 | 824 | ||
| 824 | if (self.zigObjectPtr()) |zig_object| try zig_object.flush(self, tid); | 825 | if (self.zigObjectPtr()) |zig_object| try zig_object.flush(self, tid); |
| 825 | 826 | ||
| 827 | if (module_obj_path) |path| openParseObjectReportingFailure(self, path); | ||
| 828 | |||
| 826 | switch (comp.config.output_mode) { | 829 | switch (comp.config.output_mode) { |
| 827 | .Obj => return relocatable.flushObject(self, comp, module_obj_path), | 830 | .Obj => return relocatable.flushObject(self, comp), |
| 828 | .Lib => switch (comp.config.link_mode) { | 831 | .Lib => switch (comp.config.link_mode) { |
| 829 | .dynamic => {}, | 832 | .dynamic => {}, |
| 830 | .static => return relocatable.flushStaticLib(self, comp, module_obj_path), | 833 | .static => return relocatable.flushStaticLib(self, comp), |
| 831 | }, | 834 | }, |
| 832 | .Exe => {}, | 835 | .Exe => {}, |
| 833 | } | 836 | } |
| 834 | 837 | ||
| 835 | if (module_obj_path) |path| openParseObjectReportingFailure(self, path); | ||
| 836 | |||
| 837 | if (diags.hasErrors()) return error.FlushFailure; | 838 | if (diags.hasErrors()) return error.FlushFailure; |
| 838 | 839 | ||
| 839 | // If we haven't already, create a linker-generated input file comprising of | 840 | // If we haven't already, create a linker-generated input file comprising of |
| ... | @@ -1149,7 +1150,10 @@ fn parseObject(self: *Elf, obj: link.Input.Object) ParseError!void { | ... | @@ -1149,7 +1150,10 @@ fn parseObject(self: *Elf, obj: link.Input.Object) ParseError!void { |
| 1149 | try self.objects.append(gpa, index); | 1150 | try self.objects.append(gpa, index); |
| 1150 | 1151 | ||
| 1151 | const object = self.file(index).?.object; | 1152 | const object = self.file(index).?.object; |
| 1152 | try object.parse(gpa, diags, obj.path, handle, first_eflags, target, debug_fmt_strip, default_sym_version); | 1153 | try object.parseCommon(gpa, diags, obj.path, handle, target, first_eflags); |
| 1154 | if (!self.base.isStaticLib()) { | ||
| 1155 | try object.parse(gpa, diags, obj.path, handle, target, debug_fmt_strip, default_sym_version); | ||
| 1156 | } | ||
| 1153 | } | 1157 | } |
| 1154 | 1158 | ||
| 1155 | fn parseArchive( | 1159 | fn parseArchive( |
| ... | @@ -1163,6 +1167,7 @@ fn parseArchive( | ... | @@ -1163,6 +1167,7 @@ fn parseArchive( |
| 1163 | default_sym_version: elf.Versym, | 1167 | default_sym_version: elf.Versym, |
| 1164 | objects: *std.ArrayListUnmanaged(File.Index), | 1168 | objects: *std.ArrayListUnmanaged(File.Index), |
| 1165 | obj: link.Input.Object, | 1169 | obj: link.Input.Object, |
| 1170 | is_static_lib: bool, | ||
| 1166 | ) ParseError!void { | 1171 | ) ParseError!void { |
| 1167 | const tracy = trace(@src()); | 1172 | const tracy = trace(@src()); |
| 1168 | defer tracy.end(); | 1173 | defer tracy.end(); |
| ... | @@ -1171,13 +1176,17 @@ fn parseArchive( | ... | @@ -1171,13 +1176,17 @@ fn parseArchive( |
| 1171 | var archive = try Archive.parse(gpa, diags, file_handles, obj.path, fh); | 1176 | var archive = try Archive.parse(gpa, diags, file_handles, obj.path, fh); |
| 1172 | defer archive.deinit(gpa); | 1177 | defer archive.deinit(gpa); |
| 1173 | 1178 | ||
| 1179 | const init_alive = if (is_static_lib) true else obj.must_link; | ||
| 1180 | |||
| 1174 | for (archive.objects) |extracted| { | 1181 | for (archive.objects) |extracted| { |
| 1175 | const index: File.Index = @intCast(try files.addOne(gpa)); | 1182 | const index: File.Index = @intCast(try files.addOne(gpa)); |
| 1176 | files.set(index, .{ .object = extracted }); | 1183 | files.set(index, .{ .object = extracted }); |
| 1177 | const object = &files.items(.data)[index].object; | 1184 | const object = &files.items(.data)[index].object; |
| 1178 | object.index = index; | 1185 | object.index = index; |
| 1179 | object.alive = obj.must_link; | 1186 | object.alive = init_alive; |
| 1180 | try object.parse(gpa, diags, obj.path, obj.file, first_eflags, target, debug_fmt_strip, default_sym_version); | 1187 | try object.parseCommon(gpa, diags, obj.path, obj.file, target, first_eflags); |
| 1188 | if (!is_static_lib) | ||
| 1189 | try object.parse(gpa, diags, obj.path, obj.file, target, debug_fmt_strip, default_sym_version); | ||
| 1181 | try objects.append(gpa, index); | 1190 | try objects.append(gpa, index); |
| 1182 | } | 1191 | } |
| 1183 | } | 1192 | } |
src/link/Elf/Object.zig+2-14| ... | @@ -69,13 +69,10 @@ pub fn parse( | ... | @@ -69,13 +69,10 @@ pub fn parse( |
| 69 | /// For error reporting purposes only. | 69 | /// For error reporting purposes only. |
| 70 | path: Path, | 70 | path: Path, |
| 71 | handle: fs.File, | 71 | handle: fs.File, |
| 72 | first_eflags: *?elf.Word, | ||
| 73 | target: std.Target, | 72 | target: std.Target, |
| 74 | debug_fmt_strip: bool, | 73 | debug_fmt_strip: bool, |
| 75 | default_sym_version: elf.Versym, | 74 | default_sym_version: elf.Versym, |
| 76 | ) !void { | 75 | ) !void { |
| 77 | try self.parseCommon(gpa, diags, path, handle, first_eflags, target); | ||
| 78 | |||
| 79 | // Append null input merge section | 76 | // Append null input merge section |
| 80 | try self.input_merge_sections.append(gpa, .{}); | 77 | try self.input_merge_sections.append(gpa, .{}); |
| 81 | // Allocate atom index 0 to null atom | 78 | // Allocate atom index 0 to null atom |
| ... | @@ -95,14 +92,14 @@ pub fn parse( | ... | @@ -95,14 +92,14 @@ pub fn parse( |
| 95 | } | 92 | } |
| 96 | } | 93 | } |
| 97 | 94 | ||
| 98 | fn parseCommon( | 95 | pub fn parseCommon( |
| 99 | self: *Object, | 96 | self: *Object, |
| 100 | gpa: Allocator, | 97 | gpa: Allocator, |
| 101 | diags: *Diags, | 98 | diags: *Diags, |
| 102 | path: Path, | 99 | path: Path, |
| 103 | handle: fs.File, | 100 | handle: fs.File, |
| 104 | first_eflags: *?elf.Word, | ||
| 105 | target: std.Target, | 101 | target: std.Target, |
| 102 | first_eflags: *?elf.Word, | ||
| 106 | ) !void { | 103 | ) !void { |
| 107 | const offset = if (self.archive) |ar| ar.offset else 0; | 104 | const offset = if (self.archive) |ar| ar.offset else 0; |
| 108 | const file_size = (try handle.stat()).size; | 105 | const file_size = (try handle.stat()).size; |
| ... | @@ -1036,15 +1033,6 @@ pub fn addAtomsToRelaSections(self: *Object, elf_file: *Elf) !void { | ... | @@ -1036,15 +1033,6 @@ pub fn addAtomsToRelaSections(self: *Object, elf_file: *Elf) !void { |
| 1036 | } | 1033 | } |
| 1037 | } | 1034 | } |
| 1038 | 1035 | ||
| 1039 | pub fn parseAr(self: *Object, path: Path, elf_file: *Elf) !void { | ||
| 1040 | const gpa = elf_file.base.comp.gpa; | ||
| 1041 | const diags = &elf_file.base.comp.link_diags; | ||
| 1042 | const handle = elf_file.fileHandle(self.file_handle); | ||
| 1043 | const first_eflags = &elf_file.first_eflags; | ||
| 1044 | const target = elf_file.base.comp.root_mod.resolved_target.result; | ||
| 1045 | try self.parseCommon(gpa, diags, path, handle, first_eflags, target); | ||
| 1046 | } | ||
| 1047 | |||
| 1048 | pub fn updateArSymtab(self: Object, ar_symtab: *Archive.ArSymtab, elf_file: *Elf) !void { | 1036 | pub fn updateArSymtab(self: Object, ar_symtab: *Archive.ArSymtab, elf_file: *Elf) !void { |
| 1049 | const comp = elf_file.base.comp; | 1037 | const comp = elf_file.base.comp; |
| 1050 | const gpa = comp.gpa; | 1038 | const gpa = comp.gpa; |
src/link/Elf/relocatable.zig+2-38| ... | @@ -1,11 +1,7 @@ | ... | @@ -1,11 +1,7 @@ |
| 1 | pub fn flushStaticLib(elf_file: *Elf, comp: *Compilation, module_obj_path: ?Path) link.File.FlushError!void { | 1 | pub fn flushStaticLib(elf_file: *Elf, comp: *Compilation) link.File.FlushError!void { |
| 2 | const gpa = comp.gpa; | 2 | const gpa = comp.gpa; |
| 3 | const diags = &comp.link_diags; | 3 | const diags = &comp.link_diags; |
| 4 | 4 | ||
| 5 | if (module_obj_path) |path| { | ||
| 6 | parseObjectStaticLibReportingFailure(elf_file, path); | ||
| 7 | } | ||
| 8 | |||
| 9 | if (diags.hasErrors()) return error.FlushFailure; | 5 | if (diags.hasErrors()) return error.FlushFailure; |
| 10 | 6 | ||
| 11 | // First, we flush relocatable object file generated with our backends. | 7 | // First, we flush relocatable object file generated with our backends. |
| ... | @@ -134,11 +130,9 @@ pub fn flushStaticLib(elf_file: *Elf, comp: *Compilation, module_obj_path: ?Path | ... | @@ -134,11 +130,9 @@ pub fn flushStaticLib(elf_file: *Elf, comp: *Compilation, module_obj_path: ?Path |
| 134 | if (diags.hasErrors()) return error.FlushFailure; | 130 | if (diags.hasErrors()) return error.FlushFailure; |
| 135 | } | 131 | } |
| 136 | 132 | ||
| 137 | pub fn flushObject(elf_file: *Elf, comp: *Compilation, module_obj_path: ?Path) link.File.FlushError!void { | 133 | pub fn flushObject(elf_file: *Elf, comp: *Compilation) link.File.FlushError!void { |
| 138 | const diags = &comp.link_diags; | 134 | const diags = &comp.link_diags; |
| 139 | 135 | ||
| 140 | if (module_obj_path) |path| elf_file.openParseObjectReportingFailure(path); | ||
| 141 | |||
| 142 | if (diags.hasErrors()) return error.FlushFailure; | 136 | if (diags.hasErrors()) return error.FlushFailure; |
| 143 | 137 | ||
| 144 | // Now, we are ready to resolve the symbols across all input files. | 138 | // Now, we are ready to resolve the symbols across all input files. |
| ... | @@ -188,36 +182,6 @@ pub fn flushObject(elf_file: *Elf, comp: *Compilation, module_obj_path: ?Path) l | ... | @@ -188,36 +182,6 @@ pub fn flushObject(elf_file: *Elf, comp: *Compilation, module_obj_path: ?Path) l |
| 188 | if (diags.hasErrors()) return error.FlushFailure; | 182 | if (diags.hasErrors()) return error.FlushFailure; |
| 189 | } | 183 | } |
| 190 | 184 | ||
| 191 | fn parseObjectStaticLibReportingFailure(elf_file: *Elf, path: Path) void { | ||
| 192 | const diags = &elf_file.base.comp.link_diags; | ||
| 193 | parseObjectStaticLib(elf_file, path) catch |err| switch (err) { | ||
| 194 | error.LinkFailure => return, | ||
| 195 | else => |e| diags.addParseError(path, "parsing object failed: {s}", .{@errorName(e)}), | ||
| 196 | }; | ||
| 197 | } | ||
| 198 | |||
| 199 | fn parseObjectStaticLib(elf_file: *Elf, path: Path) Elf.ParseError!void { | ||
| 200 | const gpa = elf_file.base.comp.gpa; | ||
| 201 | const file_handles = &elf_file.file_handles; | ||
| 202 | |||
| 203 | const handle = try path.root_dir.handle.openFile(path.sub_path, .{}); | ||
| 204 | const fh = try Elf.addFileHandle(gpa, file_handles, handle); | ||
| 205 | |||
| 206 | const index: File.Index = @intCast(try elf_file.files.addOne(gpa)); | ||
| 207 | elf_file.files.set(index, .{ .object = .{ | ||
| 208 | .path = .{ | ||
| 209 | .root_dir = path.root_dir, | ||
| 210 | .sub_path = try gpa.dupe(u8, path.sub_path), | ||
| 211 | }, | ||
| 212 | .file_handle = fh, | ||
| 213 | .index = index, | ||
| 214 | } }); | ||
| 215 | try elf_file.objects.append(gpa, index); | ||
| 216 | |||
| 217 | const object = elf_file.file(index).?.object; | ||
| 218 | try object.parseAr(path, elf_file); | ||
| 219 | } | ||
| 220 | |||
| 221 | fn claimUnresolved(elf_file: *Elf) void { | 185 | fn claimUnresolved(elf_file: *Elf) void { |
| 222 | if (elf_file.zigObjectPtr()) |zig_object| { | 186 | if (elf_file.zigObjectPtr()) |zig_object| { |
| 223 | zig_object.claimUnresolvedRelocatable(elf_file); | 187 | zig_object.claimUnresolvedRelocatable(elf_file); |