Commit e8e8d7e5c8
Changed files (2)
lib
compiler
resinator
lib/compiler/resinator/main.zig
@@ -120,7 +120,20 @@ pub fn main() !void {
defer aro_arena_state.deinit();
const aro_arena = aro_arena_state.allocator();
- var comp = aro.Compilation.init(aro_arena, std.fs.cwd());
+ var stderr_buf: [512]u8 = undefined;
+ var stderr_writer = stderr.writer(&stderr_buf);
+ var diagnostics: aro.Diagnostics = switch (zig_integration) {
+ false => .{ .output = .{ .to_writer = .{
+ .writer = &stderr_writer.interface,
+ .color = stderr_config,
+ } } },
+ true => .{ .output = .{ .to_list = .{
+ .arena = .init(allocator),
+ } } },
+ };
+ defer diagnostics.deinit();
+
+ var comp = aro.Compilation.init(aro_arena, aro_arena, &diagnostics, std.fs.cwd());
defer comp.deinit();
var argv: std.ArrayList([]const u8) = .empty;
@@ -143,20 +156,24 @@ pub fn main() !void {
try stdout.flush();
}
- preprocess.preprocess(&comp, &preprocessed_buf.writer, argv.items, maybe_dependencies) catch |err| switch (err) {
+ preprocess.preprocess(&comp, &preprocessed_buf.writer, argv.items, maybe_dependencies_list) catch |err| switch (err) {
error.GeneratedSourceError => {
- try error_handler.emitAroDiagnostics(allocator, "failed during preprocessor setup (this is always a bug):", &comp);
+ try error_handler.emitAroDiagnostics(allocator, "failed during preprocessor setup (this is always a bug)", &comp);
std.process.exit(1);
},
// ArgError can occur if e.g. the .rc file is not found
error.ArgError, error.PreprocessError => {
- try error_handler.emitAroDiagnostics(allocator, "failed during preprocessing:", &comp);
+ try error_handler.emitAroDiagnostics(allocator, "failed during preprocessing", &comp);
std.process.exit(1);
},
- error.StreamTooLong => {
+ error.FileTooBig => {
try error_handler.emitMessage(allocator, .err, "failed during preprocessing: maximum file size exceeded", .{});
std.process.exit(1);
},
+ error.WriteFailed => {
+ try error_handler.emitMessage(allocator, .err, "failed during preprocessing: error writing the preprocessed output", .{});
+ std.process.exit(1);
+ },
error.OutOfMemory => |e| return e,
};
@@ -660,11 +677,10 @@ const ErrorHandler = union(enum) {
try server.serveErrorBundle(error_bundle);
},
.tty => {
- // extra newline to separate this line from the aro errors
+ // aro errors have already been emitted
const stderr = std.debug.lockStderrWriter(&.{});
defer std.debug.unlockStderrWriter();
- try renderErrorMessage(stderr, self.tty, .err, "{s}\n", .{fail_msg});
- aro.Diagnostics.render(comp, self.tty);
+ try renderErrorMessage(stderr, self.tty, .err, "{s}", .{fail_msg});
},
}
}
@@ -883,12 +899,10 @@ fn aroDiagnosticsToErrorBundle(
.msg = try bundle.addString(fail_msg),
});
- var msg_writer = MsgWriter.init(gpa);
- defer msg_writer.deinit();
var cur_err: ?ErrorBundle.ErrorMessage = null;
var cur_notes: std.ArrayList(ErrorBundle.ErrorMessage) = .empty;
defer cur_notes.deinit(gpa);
- for (comp.diagnostics.list.items) |msg| {
+ for (comp.diagnostics.output.to_list.messages.items) |msg| {
switch (msg.kind) {
// Clear the current error so that notes don't bleed into unassociated errors
.off, .warning => {
@@ -897,28 +911,19 @@ fn aroDiagnosticsToErrorBundle(
},
.note => if (cur_err == null) continue,
.@"fatal error", .@"error" => {},
- .default => unreachable,
}
- msg_writer.resetRetainingCapacity();
- aro.Diagnostics.renderMessage(comp, &msg_writer, msg);
const src_loc = src_loc: {
- if (msg_writer.path) |src_path| {
- var src_loc: ErrorBundle.SourceLocation = .{
- .src_path = try bundle.addString(src_path),
- .line = msg_writer.line - 1, // 1-based -> 0-based
- .column = msg_writer.col - 1, // 1-based -> 0-based
- .span_start = 0,
- .span_main = 0,
- .span_end = 0,
- };
- if (msg_writer.source_line) |source_line| {
- src_loc.span_start = msg_writer.span_main;
- src_loc.span_main = msg_writer.span_main;
- src_loc.span_end = msg_writer.span_main;
- src_loc.source_line = try bundle.addString(source_line);
- }
- break :src_loc try bundle.addSourceLocation(src_loc);
+ if (msg.location) |location| {
+ break :src_loc try bundle.addSourceLocation(.{
+ .src_path = try bundle.addString(location.path),
+ .line = location.line_no - 1, // 1-based -> 0-based
+ .column = location.col - 1, // 1-based -> 0-based
+ .span_start = location.width,
+ .span_main = location.width,
+ .span_end = location.width,
+ .source_line = try bundle.addString(location.line),
+ });
}
break :src_loc ErrorBundle.SourceLocationIndex.none;
};
@@ -929,7 +934,7 @@ fn aroDiagnosticsToErrorBundle(
try flushErrorMessageIntoBundle(&bundle, err, cur_notes.items);
}
cur_err = .{
- .msg = try bundle.addString(msg_writer.buf.items),
+ .msg = try bundle.addString(msg.text),
.src_loc = src_loc,
};
cur_notes.clearRetainingCapacity();
@@ -937,11 +942,11 @@ fn aroDiagnosticsToErrorBundle(
.note => {
cur_err.?.notes_len += 1;
try cur_notes.append(gpa, .{
- .msg = try bundle.addString(msg_writer.buf.items),
+ .msg = try bundle.addString(msg.text),
.src_loc = src_loc,
});
},
- .off, .warning, .default => unreachable,
+ .off, .warning => unreachable,
}
}
if (cur_err) |err| {
@@ -950,63 +955,3 @@ fn aroDiagnosticsToErrorBundle(
return try bundle.toOwnedBundle("");
}
-
-// Similar to aro.Diagnostics.MsgWriter but:
-// - Writers to an ArrayList
-// - Only prints the message itself (no location, source line, error: prefix, etc)
-// - Keeps track of source path/line/col instead
-const MsgWriter = struct {
- buf: std.array_list.Managed(u8),
- path: ?[]const u8 = null,
- // 1-indexed
- line: u32 = undefined,
- col: u32 = undefined,
- source_line: ?[]const u8 = null,
- span_main: u32 = undefined,
-
- fn init(allocator: std.mem.Allocator) MsgWriter {
- return .{
- .buf = std.array_list.Managed(u8).init(allocator),
- };
- }
-
- fn deinit(m: *MsgWriter) void {
- m.buf.deinit();
- }
-
- fn resetRetainingCapacity(m: *MsgWriter) void {
- m.buf.clearRetainingCapacity();
- m.path = null;
- m.source_line = null;
- }
-
- pub fn print(m: *MsgWriter, comptime fmt: []const u8, args: anytype) void {
- m.buf.print(fmt, args) catch {};
- }
-
- pub fn write(m: *MsgWriter, msg: []const u8) void {
- m.buf.appendSlice(msg) catch {};
- }
-
- pub fn setColor(m: *MsgWriter, color: std.Io.tty.Color) void {
- _ = m;
- _ = color;
- }
-
- pub fn location(m: *MsgWriter, path: []const u8, line: u32, col: u32) void {
- m.path = path;
- m.line = line;
- m.col = col;
- }
-
- pub fn start(m: *MsgWriter, kind: aro.Diagnostics.Kind) void {
- _ = m;
- _ = kind;
- }
-
- pub fn end(m: *MsgWriter, maybe_line: ?[]const u8, col: u32, end_with_splice: bool) void {
- _ = end_with_splice;
- m.source_line = maybe_line;
- m.span_main = col;
- }
-};
lib/compiler/resinator/preprocess.zig
@@ -5,7 +5,7 @@ const cli = @import("cli.zig");
const Dependencies = @import("compile.zig").Dependencies;
const aro = @import("aro");
-const PreprocessError = error{ ArgError, GeneratedSourceError, PreprocessError, StreamTooLong, OutOfMemory };
+const PreprocessError = error{ ArgError, GeneratedSourceError, PreprocessError, FileTooBig, OutOfMemory, WriteFailed };
pub fn preprocess(
comp: *aro.Compilation,
@@ -16,18 +16,18 @@ pub fn preprocess(
) PreprocessError!void {
try comp.addDefaultPragmaHandlers();
- var driver: aro.Driver = .{ .comp = comp, .aro_name = "arocc" };
+ var driver: aro.Driver = .{ .comp = comp, .diagnostics = comp.diagnostics, .aro_name = "arocc" };
defer driver.deinit();
- var macro_buf: std.Io.Writer.Allocating = .init(comp.gpa);
- defer macro_buf.deinit();
+ var macro_buf: std.ArrayListUnmanaged(u8) = .empty;
+ defer macro_buf.deinit(comp.gpa);
- var trash: [64]u8 = undefined;
- var discarding: std.Io.Writer.Discarding = .init(&trash);
- _ = driver.parseArgs(&discarding.writer, ¯o_buf.writer, argv) catch |err| switch (err) {
+ var discard_buffer: [64]u8 = undefined;
+ var discarding: std.Io.Writer.Discarding = .init(&discard_buffer);
+ _ = driver.parseArgs(&discarding.writer, ¯o_buf, argv) catch |err| switch (err) {
error.FatalError => return error.ArgError,
error.OutOfMemory => |e| return e,
- error.WriteFailed => return error.OutOfMemory,
+ error.WriteFailed => unreachable,
};
if (hasAnyErrors(comp)) return error.ArgError;
@@ -46,7 +46,10 @@ pub fn preprocess(
if (hasAnyErrors(comp)) return error.GeneratedSourceError;
comp.generated_buf.items.len = 0;
- var pp = try aro.Preprocessor.initDefault(comp);
+ var pp = aro.Preprocessor.initDefault(comp) catch |err| switch (err) {
+ error.FatalError => return error.GeneratedSourceError,
+ error.OutOfMemory => |e| return e,
+ };
defer pp.deinit();
if (comp.langopts.ms_extensions) {
@@ -79,16 +82,7 @@ pub fn preprocess(
}
fn hasAnyErrors(comp: *aro.Compilation) bool {
- // In theory we could just check Diagnostics.errors != 0, but that only
- // gets set during rendering of the error messages, see:
- // https://github.com/Vexu/arocc/issues/603
- for (comp.diagnostics.list.items) |msg| {
- switch (msg.kind) {
- .@"fatal error", .@"error" => return true,
- else => {},
- }
- }
- return false;
+ return comp.diagnostics.errors != 0;
}
/// `arena` is used for temporary -D argument strings and the INCLUDE environment variable.