Skip to content

Commit 080dd27

Browse files
committed
breaking: fix @typeinfo handling of global error set type
`builtin.TypeInfo.ErrorSet` is now `?[]Error` instead of `struct{errors:[]Error}`. closes #1936
1 parent e861da0 commit 080dd27

File tree

7 files changed

+17
-49
lines changed

7 files changed

+17
-49
lines changed

doc/docgen.zig

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -707,7 +707,7 @@ const builtin_types = [][]const u8{
707707
"f16", "f32", "f64", "f128", "c_longdouble", "c_short",
708708
"c_ushort", "c_int", "c_uint", "c_long", "c_ulong", "c_longlong",
709709
"c_ulonglong", "c_char", "c_void", "void", "bool", "isize",
710-
"usize", "noreturn", "type", "error", "comptime_int", "comptime_float",
710+
"usize", "noreturn", "type", "anyerror", "comptime_int", "comptime_float",
711711
};
712712

713713
fn isType(name: []const u8) bool {

src/codegen.cpp

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7581,9 +7581,7 @@ Buf *codegen_generate_builtin_source(CodeGen *g) {
75817581
" value: comptime_int,\n"
75827582
" };\n"
75837583
"\n"
7584-
" pub const ErrorSet = struct {\n"
7585-
" errors: []Error,\n"
7586-
" };\n"
7584+
" pub const ErrorSet = ?[]Error;\n"
75877585
"\n"
75887586
" pub const EnumField = struct {\n"
75897587
" name: []const u8,\n"

src/ir.cpp

Lines changed: 5 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -18265,21 +18265,16 @@ static Error ir_make_type_info_value(IrAnalyze *ira, IrInstruction *source_instr
1826518265
result->special = ConstValSpecialStatic;
1826618266
result->type = ir_type_info_get_type(ira, "ErrorSet", nullptr);
1826718267

18268-
ConstExprValue *fields = create_const_vals(1);
18269-
result->data.x_struct.fields = fields;
18270-
18271-
// errors: []TypeInfo.Error
18272-
ensure_field_index(result->type, "errors", 0);
18273-
1827418268
ZigType *type_info_error_type = ir_type_info_get_type(ira, "Error", nullptr);
1827518269
if (!resolve_inferred_error_set(ira->codegen, type_entry, source_instr->source_node)) {
1827618270
return ErrorSemanticAnalyzeFail;
1827718271
}
1827818272
if (type_is_global_error_set(type_entry)) {
18279-
ir_add_error(ira, source_instr,
18280-
buf_sprintf("TODO: compiler bug: implement @typeInfo support for anyerror. https://github.com/ziglang/zig/issues/1936"));
18281-
return ErrorSemanticAnalyzeFail;
18273+
result->data.x_optional = nullptr;
18274+
break;
1828218275
}
18276+
ConstExprValue *slice_val = create_const_vals(1);
18277+
result->data.x_optional = slice_val;
1828318278

1828418279
uint32_t error_count = type_entry->data.error_set.err_count;
1828518280
ConstExprValue *error_array = create_const_vals(1);
@@ -18288,7 +18283,7 @@ static Error ir_make_type_info_value(IrAnalyze *ira, IrInstruction *source_instr
1828818283
error_array->data.x_array.special = ConstArraySpecialNone;
1828918284
error_array->data.x_array.data.s_none.elements = create_const_vals(error_count);
1829018285

18291-
init_const_slice(ira->codegen, &fields[0], error_array, 0, error_count, false);
18286+
init_const_slice(ira->codegen, slice_val, error_array, 0, error_count, false);
1829218287
for (uint32_t error_index = 0; error_index < error_count; error_index++) {
1829318288
ErrorTableEntry *error = type_entry->data.error_set.errors[error_index];
1829418289
ConstExprValue *error_val = &error_array->data.x_array.data.s_none.elements[error_index];

std/fmt.zig

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -112,10 +112,6 @@ pub fn formatType(
112112
output: fn (@typeOf(context), []const u8) Errors!void,
113113
) Errors!void {
114114
const T = @typeOf(value);
115-
if (T == anyerror) {
116-
try output(context, "error.");
117-
return output(context, @errorName(value));
118-
}
119115
switch (@typeInfo(T)) {
120116
builtin.TypeId.ComptimeInt, builtin.TypeId.Int, builtin.TypeId.Float => {
121117
return formatValue(value, fmt, context, Errors, output);

std/meta.zig

Lines changed: 3 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -13,32 +13,8 @@ const TypeInfo = builtin.TypeInfo;
1313
pub fn tagName(v: var) []const u8 {
1414
const T = @typeOf(v);
1515
switch (@typeInfo(T)) {
16-
TypeId.Enum => |info| {
17-
const Tag = info.tag_type;
18-
inline for (info.fields) |field| {
19-
if (field.value == @enumToInt(v)) return field.name;
20-
}
21-
22-
unreachable;
23-
},
24-
TypeId.Union => |info| {
25-
const UnionTag = if (info.tag_type) |UT| UT else @compileError("union is untagged");
26-
const Tag = @typeInfo(UnionTag).Enum.tag_type;
27-
inline for (info.fields) |field| {
28-
if (field.enum_field.?.value == @enumToInt(UnionTag(v)))
29-
return field.name;
30-
}
31-
32-
unreachable;
33-
},
34-
TypeId.ErrorSet => |info| {
35-
inline for (info.errors) |err| {
36-
if (err.value == @errorToInt(v)) return err.name;
37-
}
38-
39-
unreachable;
40-
},
41-
else => @compileError("expected enum, error set or union type, found '" ++ @typeName(T) ++ "'"),
16+
TypeId.ErrorSet => return @errorName(v),
17+
else => return @tagName(v),
4218
}
4319
}
4420

@@ -267,7 +243,7 @@ pub fn fields(comptime T: type) switch (@typeInfo(T)) {
267243
TypeId.Struct => |info| info.fields,
268244
TypeId.Union => |info| info.fields,
269245
TypeId.Enum => |info| info.fields,
270-
TypeId.ErrorSet => |info| info.errors,
246+
TypeId.ErrorSet => |errors| errors.?, // must be non global error set
271247
else => @compileError("Expected struct, union, error set or enum type, found '" ++ @typeName(T) ++ "'"),
272248
};
273249
}

std/testing.zig

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@ const std = @import("std.zig");
55
/// This function is intended to be used only in tests. It prints diagnostics to stderr
66
/// and then aborts when actual_error_union is not expected_error.
77
pub fn expectError(expected_error: anyerror, actual_error_union: var) void {
8-
// TODO remove the workaround here for https://github.com/ziglang/zig/issues/1936
98
if (actual_error_union) |actual_payload| {
109
// TODO remove workaround here for https://github.com/ziglang/zig/issues/557
1110
if (@sizeOf(@typeOf(actual_payload)) == 0) {

test/stage1/behavior/type_info.zig

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -143,14 +143,18 @@ fn testErrorSet() void {
143143

144144
const error_set_info = @typeInfo(TestErrorSet);
145145
expect(TypeId(error_set_info) == TypeId.ErrorSet);
146-
expect(error_set_info.ErrorSet.errors.len == 3);
147-
expect(mem.eql(u8, error_set_info.ErrorSet.errors[0].name, "First"));
148-
expect(error_set_info.ErrorSet.errors[2].value == @errorToInt(TestErrorSet.Third));
146+
expect(error_set_info.ErrorSet.?.len == 3);
147+
expect(mem.eql(u8, error_set_info.ErrorSet.?[0].name, "First"));
148+
expect(error_set_info.ErrorSet.?[2].value == @errorToInt(TestErrorSet.Third));
149149

150150
const error_union_info = @typeInfo(TestErrorSet!usize);
151151
expect(TypeId(error_union_info) == TypeId.ErrorUnion);
152152
expect(error_union_info.ErrorUnion.error_set == TestErrorSet);
153153
expect(error_union_info.ErrorUnion.payload == usize);
154+
155+
const global_info = @typeInfo(anyerror);
156+
expect(TypeId(global_info) == TypeId.ErrorSet);
157+
expect(global_info.ErrorSet == null);
154158
}
155159

156160
test "type info: enum info" {

0 commit comments

Comments
 (0)