| ... | @@ -3769,9 +3769,7 @@ pub fn cmdFmt(gpa: Allocator, arena: Allocator, args: []const []const u8) !void | ... | @@ -3769,9 +3769,7 @@ pub fn cmdFmt(gpa: Allocator, arena: Allocator, args: []const []const u8) !void |
| 3769 | }; | 3769 | }; |
| 3770 | defer tree.deinit(gpa); | 3770 | defer tree.deinit(gpa); |
| 3771 | | 3771 | |
| 3772 | for (tree.errors) |parse_error| { | 3772 | try printErrsMsgToStdErr(gpa, arena, tree.errors, tree, "<stdin>", color); |
| 3773 | try printErrMsgToStdErr(gpa, arena, parse_error, tree, "<stdin>", color); | | |
| 3774 | } | | |
| 3775 | var has_ast_error = false; | 3773 | var has_ast_error = false; |
| 3776 | if (check_ast_flag) { | 3774 | if (check_ast_flag) { |
| 3777 | const Module = @import("Module.zig"); | 3775 | const Module = @import("Module.zig"); |
| ... | @@ -3959,9 +3957,7 @@ fn fmtPathFile( | ... | @@ -3959,9 +3957,7 @@ fn fmtPathFile( |
| 3959 | var tree = try std.zig.parse(fmt.gpa, source_code); | 3957 | var tree = try std.zig.parse(fmt.gpa, source_code); |
| 3960 | defer tree.deinit(fmt.gpa); | 3958 | defer tree.deinit(fmt.gpa); |
| 3961 | | 3959 | |
| 3962 | for (tree.errors) |parse_error| { | 3960 | try printErrsMsgToStdErr(fmt.gpa, fmt.arena, tree.errors, tree, file_path, fmt.color); |
| 3963 | try printErrMsgToStdErr(fmt.gpa, fmt.arena, parse_error, tree, file_path, fmt.color); | | |
| 3964 | } | | |
| 3965 | if (tree.errors.len != 0) { | 3961 | if (tree.errors.len != 0) { |
| 3966 | fmt.any_error = true; | 3962 | fmt.any_error = true; |
| 3967 | return; | 3963 | return; |
| ... | @@ -4041,66 +4037,95 @@ fn fmtPathFile( | ... | @@ -4041,66 +4037,95 @@ fn fmtPathFile( |
| 4041 | } | 4037 | } |
| 4042 | } | 4038 | } |
| 4043 | | 4039 | |
| 4044 | fn printErrMsgToStdErr( | 4040 | fn printErrsMsgToStdErr( |
| 4045 | gpa: mem.Allocator, | 4041 | gpa: mem.Allocator, |
| 4046 | arena: mem.Allocator, | 4042 | arena: mem.Allocator, |
| 4047 | parse_error: Ast.Error, | 4043 | parse_errors: []const Ast.Error, |
| 4048 | tree: Ast, | 4044 | tree: Ast, |
| 4049 | path: []const u8, | 4045 | path: []const u8, |
| 4050 | color: Color, | 4046 | color: Color, |
| 4051 | ) !void { | 4047 | ) !void { |
| 4052 | const lok_token = parse_error.token; | 4048 | var i: usize = 0; |
| 4053 | const token_tags = tree.tokens.items(.tag); | 4049 | while (i < parse_errors.len) : (i += 1) { |
| 4054 | const start_loc = tree.tokenLocation(0, lok_token); | 4050 | const parse_error = parse_errors[i]; |
| 4055 | const source_line = tree.source[start_loc.line_start..start_loc.line_end]; | 4051 | const lok_token = parse_error.token; |
| 4056 | | 4052 | const token_tags = tree.tokens.items(.tag); |
| 4057 | var text_buf = std.ArrayList(u8).init(gpa); | 4053 | const start_loc = tree.tokenLocation(0, lok_token); |
| 4058 | defer text_buf.deinit(); | 4054 | const source_line = tree.source[start_loc.line_start..start_loc.line_end]; |
| 4059 | const writer = text_buf.writer(); | 4055 | |
| 4060 | try tree.renderError(parse_error, writer); | 4056 | var text_buf = std.ArrayList(u8).init(gpa); |
| 4061 | const text = text_buf.items; | 4057 | defer text_buf.deinit(); |
| 4062 | | 4058 | const writer = text_buf.writer(); |
| 4063 | var notes_buffer: [1]Compilation.AllErrors.Message = undefined; | 4059 | try tree.renderError(parse_error, writer); |
| 4064 | var notes_len: usize = 0; | 4060 | const text = text_buf.items; |
| 4065 | | 4061 | |
| 4066 | if (token_tags[parse_error.token + @boolToInt(parse_error.token_is_prev)] == .invalid) { | 4062 | var notes_buffer: [2]Compilation.AllErrors.Message = undefined; |
| 4067 | const bad_off = @intCast(u32, tree.tokenSlice(parse_error.token + @boolToInt(parse_error.token_is_prev)).len); | 4063 | var notes_len: usize = 0; |
| 4068 | const byte_offset = @intCast(u32, start_loc.line_start) + @intCast(u32, start_loc.column) + bad_off; | 4064 | |
| 4069 | notes_buffer[notes_len] = .{ | 4065 | if (token_tags[parse_error.token + @boolToInt(parse_error.token_is_prev)] == .invalid) { |
| | 4066 | const bad_off = @intCast(u32, tree.tokenSlice(parse_error.token + @boolToInt(parse_error.token_is_prev)).len); |
| | 4067 | const byte_offset = @intCast(u32, start_loc.line_start) + @intCast(u32, start_loc.column) + bad_off; |
| | 4068 | notes_buffer[notes_len] = .{ |
| | 4069 | .src = .{ |
| | 4070 | .src_path = path, |
| | 4071 | .msg = try std.fmt.allocPrint(arena, "invalid byte: '{'}'", .{ |
| | 4072 | std.zig.fmtEscapes(tree.source[byte_offset..][0..1]), |
| | 4073 | }), |
| | 4074 | .byte_offset = byte_offset, |
| | 4075 | .line = @intCast(u32, start_loc.line), |
| | 4076 | .column = @intCast(u32, start_loc.column) + bad_off, |
| | 4077 | .source_line = source_line, |
| | 4078 | }, |
| | 4079 | }; |
| | 4080 | notes_len += 1; |
| | 4081 | } else if (parse_error.tag == .decl_between_fields) { |
| | 4082 | const prev_loc = tree.tokenLocation(0, parse_errors[i + 1].token); |
| | 4083 | notes_buffer[0] = .{ |
| | 4084 | .src = .{ |
| | 4085 | .src_path = path, |
| | 4086 | .msg = "field before declarations here", |
| | 4087 | .byte_offset = @intCast(u32, prev_loc.line_start), |
| | 4088 | .line = @intCast(u32, prev_loc.line), |
| | 4089 | .column = @intCast(u32, prev_loc.column), |
| | 4090 | .source_line = tree.source[prev_loc.line_start..prev_loc.line_end], |
| | 4091 | }, |
| | 4092 | }; |
| | 4093 | const next_loc = tree.tokenLocation(0, parse_errors[i + 2].token); |
| | 4094 | notes_buffer[1] = .{ |
| | 4095 | .src = .{ |
| | 4096 | .src_path = path, |
| | 4097 | .msg = "field after declarations here", |
| | 4098 | .byte_offset = @intCast(u32, next_loc.line_start), |
| | 4099 | .line = @intCast(u32, next_loc.line), |
| | 4100 | .column = @intCast(u32, next_loc.column), |
| | 4101 | .source_line = tree.source[next_loc.line_start..next_loc.line_end], |
| | 4102 | }, |
| | 4103 | }; |
| | 4104 | notes_len = 2; |
| | 4105 | i += 2; |
| | 4106 | } |
| | 4107 | |
| | 4108 | const extra_offset = tree.errorOffset(parse_error); |
| | 4109 | const message: Compilation.AllErrors.Message = .{ |
| 4070 | .src = .{ | 4110 | .src = .{ |
| 4071 | .src_path = path, | 4111 | .src_path = path, |
| 4072 | .msg = try std.fmt.allocPrint(arena, "invalid byte: '{'}'", .{ | 4112 | .msg = text, |
| 4073 | std.zig.fmtEscapes(tree.source[byte_offset..][0..1]), | 4113 | .byte_offset = @intCast(u32, start_loc.line_start) + extra_offset, |
| 4074 | }), | | |
| 4075 | .byte_offset = byte_offset, | | |
| 4076 | .line = @intCast(u32, start_loc.line), | 4114 | .line = @intCast(u32, start_loc.line), |
| 4077 | .column = @intCast(u32, start_loc.column) + bad_off, | 4115 | .column = @intCast(u32, start_loc.column) + extra_offset, |
| 4078 | .source_line = source_line, | 4116 | .source_line = source_line, |
| | 4117 | .notes = notes_buffer[0..notes_len], |
| 4079 | }, | 4118 | }, |
| 4080 | }; | 4119 | }; |
| 4081 | notes_len += 1; | | |
| 4082 | } | | |
| 4083 | | 4120 | |
| 4084 | const extra_offset = tree.errorOffset(parse_error); | 4121 | const ttyconf: std.debug.TTY.Config = switch (color) { |
| 4085 | const message: Compilation.AllErrors.Message = .{ | 4122 | .auto => std.debug.detectTTYConfig(), |
| 4086 | .src = .{ | 4123 | .on => .escape_codes, |
| 4087 | .src_path = path, | 4124 | .off => .no_color, |
| 4088 | .msg = text, | 4125 | }; |
| 4089 | .byte_offset = @intCast(u32, start_loc.line_start) + extra_offset, | | |
| 4090 | .line = @intCast(u32, start_loc.line), | | |
| 4091 | .column = @intCast(u32, start_loc.column) + extra_offset, | | |
| 4092 | .source_line = source_line, | | |
| 4093 | .notes = notes_buffer[0..notes_len], | | |
| 4094 | }, | | |
| 4095 | }; | | |
| 4096 | | | |
| 4097 | const ttyconf: std.debug.TTY.Config = switch (color) { | | |
| 4098 | .auto => std.debug.detectTTYConfig(), | | |
| 4099 | .on => .escape_codes, | | |
| 4100 | .off => .no_color, | | |
| 4101 | }; | | |
| 4102 | | 4126 | |
| 4103 | message.renderToStdErr(ttyconf); | 4127 | message.renderToStdErr(ttyconf); |
| | 4128 | } |
| 4104 | } | 4129 | } |
| 4105 | | 4130 | |
| 4106 | pub const info_zen = | 4131 | pub const info_zen = |
| ... | @@ -4658,9 +4683,7 @@ pub fn cmdAstCheck( | ... | @@ -4658,9 +4683,7 @@ pub fn cmdAstCheck( |
| 4658 | file.tree_loaded = true; | 4683 | file.tree_loaded = true; |
| 4659 | defer file.tree.deinit(gpa); | 4684 | defer file.tree.deinit(gpa); |
| 4660 | | 4685 | |
| 4661 | for (file.tree.errors) |parse_error| { | 4686 | try printErrsMsgToStdErr(gpa, arena, file.tree.errors, file.tree, file.sub_file_path, color); |
| 4662 | try printErrMsgToStdErr(gpa, arena, parse_error, file.tree, file.sub_file_path, color); | | |
| 4663 | } | | |
| 4664 | if (file.tree.errors.len != 0) { | 4687 | if (file.tree.errors.len != 0) { |
| 4665 | process.exit(1); | 4688 | process.exit(1); |
| 4666 | } | 4689 | } |
| ... | @@ -4786,9 +4809,7 @@ pub fn cmdChangelist( | ... | @@ -4786,9 +4809,7 @@ pub fn cmdChangelist( |
| 4786 | file.tree_loaded = true; | 4809 | file.tree_loaded = true; |
| 4787 | defer file.tree.deinit(gpa); | 4810 | defer file.tree.deinit(gpa); |
| 4788 | | 4811 | |
| 4789 | for (file.tree.errors) |parse_error| { | 4812 | try printErrsMsgToStdErr(gpa, arena, file.tree.errors, file.tree, old_source_file, .auto); |
| 4790 | try printErrMsgToStdErr(gpa, arena, parse_error, file.tree, old_source_file, .auto); | | |
| 4791 | } | | |
| 4792 | if (file.tree.errors.len != 0) { | 4813 | if (file.tree.errors.len != 0) { |
| 4793 | process.exit(1); | 4814 | process.exit(1); |
| 4794 | } | 4815 | } |
| ... | @@ -4825,9 +4846,7 @@ pub fn cmdChangelist( | ... | @@ -4825,9 +4846,7 @@ pub fn cmdChangelist( |
| 4825 | var new_tree = try std.zig.parse(gpa, new_source); | 4846 | var new_tree = try std.zig.parse(gpa, new_source); |
| 4826 | defer new_tree.deinit(gpa); | 4847 | defer new_tree.deinit(gpa); |
| 4827 | | 4848 | |
| 4828 | for (new_tree.errors) |parse_error| { | 4849 | try printErrsMsgToStdErr(gpa, arena, new_tree.errors, new_tree, new_source_file, .auto); |
| 4829 | try printErrMsgToStdErr(gpa, arena, parse_error, new_tree, new_source_file, .auto); | | |
| 4830 | } | | |
| 4831 | if (new_tree.errors.len != 0) { | 4850 | if (new_tree.errors.len != 0) { |
| 4832 | process.exit(1); | 4851 | process.exit(1); |
| 4833 | } | 4852 | } |