Commit 3df58a9583
Changed files (1)
src
link
src/link/Elf.zig
@@ -980,6 +980,16 @@ pub fn flushModule(self: *Elf, comp: *Compilation, prog_node: *std.Progress.Node
};
_ = compiler_rt_path;
+ // Parse input files
+ for (self.base.options.objects) |obj| {
+ const in_file = try std.fs.cwd().openFile(obj.path, .{});
+ defer in_file.close();
+
+ var parse_ctx: ParseErrorCtx = .{ .detected_cpu_arch = undefined };
+ self.parsePositional(in_file, obj.path, obj.must_link, &parse_ctx) catch |err|
+ try self.handleAndReportParseError(obj.path, err, &parse_ctx);
+ }
+
if (self.lazy_syms.getPtr(.none)) |metadata| {
// Most lazy symbols can be updated on first use, but
// anyerror needs to wait for everything to be flushed.
@@ -1246,6 +1256,36 @@ pub fn flushModule(self: *Elf, comp: *Compilation, prog_node: *std.Progress.Node
assert(!self.got.dirty);
}
+const ParseError = error{
+ UnknownFileType,
+ InvalidCpuArch,
+ OutOfMemory,
+ Overflow,
+ InputOutput,
+ EndOfStream,
+ FileSystem,
+ NotSupported,
+} || std.os.SeekError || std.fs.File.OpenError || std.fs.File.ReadError;
+
+fn parsePositional(
+ self: *Elf,
+ in_file: std.fs.File,
+ path: []const u8,
+ must_link: bool,
+ ctx: *ParseErrorCtx,
+) ParseError!void {
+ const tracy = trace(@src());
+ defer tracy.end();
+
+ _ = self;
+ _ = in_file;
+ _ = path;
+ _ = must_link;
+ _ = ctx;
+
+ return error.UnknownFileType;
+}
+
fn linkWithLLD(self: *Elf, comp: *Compilation, prog_node: *std.Progress.Node) !void {
const tracy = trace(@src());
defer tracy.end();
@@ -3451,6 +3491,49 @@ fn reportUndefined(self: *Elf) !void {
}
}
+const ParseErrorCtx = struct {
+ detected_cpu_arch: std.Target.Cpu.Arch,
+};
+
+fn handleAndReportParseError(
+ self: *Elf,
+ path: []const u8,
+ err: ParseError,
+ ctx: *const ParseErrorCtx,
+) error{OutOfMemory}!void {
+ const cpu_arch = self.base.options.target.cpu.arch;
+ switch (err) {
+ error.UnknownFileType => try self.reportParseError(path, "unknown file type", .{}),
+ error.InvalidCpuArch => try self.reportParseError(
+ path,
+ "invalid cpu architecture: expected '{s}', but found '{s}'",
+ .{ @tagName(cpu_arch), @tagName(ctx.detected_cpu_arch) },
+ ),
+ else => |e| try self.reportParseError(
+ path,
+ "unexpected error: parsing object failed with error {s}",
+ .{@errorName(e)},
+ ),
+ }
+}
+
+fn reportParseError(
+ self: *Elf,
+ path: []const u8,
+ comptime format: []const u8,
+ args: anytype,
+) error{OutOfMemory}!void {
+ const gpa = self.base.allocator;
+ try self.misc_errors.ensureUnusedCapacity(gpa, 1);
+ var notes = try gpa.alloc(link.File.ErrorMsg, 1);
+ errdefer gpa.free(notes);
+ notes[0] = .{ .msg = try std.fmt.allocPrint(gpa, "while parsing {s}", .{path}) };
+ self.misc_errors.appendAssumeCapacity(.{
+ .msg = try std.fmt.allocPrint(gpa, format, args),
+ .notes = notes,
+ });
+}
+
fn dumpState(self: *Elf) std.fmt.Formatter(fmtDumpState) {
return .{ .data = self };
}