Commit 746435a954
Changed files (3)
test
behavior
src/Sema.zig
@@ -4192,12 +4192,12 @@ fn analyzeCall(
.auto,
.always_inline,
.compile_time,
+ .no_async,
=> {},
.async_kw,
.never_tail,
.never_inline,
- .no_async,
.always_tail,
=> return sema.fail(block, call_src, "TODO implement call with modifier {}", .{
modifier,
@@ -10035,51 +10035,93 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai
var buffer: Value.ToTypeBuffer = undefined;
break :t try struct_field_ty_decl.val.toType(&buffer).copy(fields_anon_decl.arena());
};
-
const struct_ty = try sema.resolveTypeFields(block, src, ty);
- const struct_fields = struct_ty.structFields();
- const struct_field_vals = try fields_anon_decl.arena().alloc(Value, struct_fields.count());
const layout = struct_ty.containerLayout();
- for (struct_field_vals) |*field_val, i| {
- const field = struct_fields.values()[i];
- const name = struct_fields.keys()[i];
- const name_val = v: {
- var anon_decl = try block.startAnonDecl(src);
- defer anon_decl.deinit();
- const bytes = try anon_decl.arena().dupeZ(u8, name);
- const new_decl = try anon_decl.finish(
- try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len),
- try Value.Tag.bytes.create(anon_decl.arena(), bytes[0 .. bytes.len + 1]),
- );
- break :v try Value.Tag.decl_ref.create(fields_anon_decl.arena(), new_decl);
- };
+ const struct_field_vals = fv: {
+ if (struct_ty.castTag(.tuple)) |payload| {
+ const field_types = payload.data.types;
+ const struct_field_vals = try fields_anon_decl.arena().alloc(Value, field_types.len);
+ for (struct_field_vals) |*struct_field_val, i| {
+ const field_ty = field_types[i];
+ const name_val = v: {
+ var anon_decl = try block.startAnonDecl(src);
+ defer anon_decl.deinit();
+ const bytes = try std.fmt.allocPrintZ(anon_decl.arena(), "{d}", .{i});
+ const new_decl = try anon_decl.finish(
+ try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len),
+ try Value.Tag.bytes.create(anon_decl.arena(), bytes[0 .. bytes.len + 1]),
+ );
+ break :v try Value.Tag.decl_ref.create(fields_anon_decl.arena(), new_decl);
+ };
- const struct_field_fields = try fields_anon_decl.arena().create([5]Value);
- const opt_default_val = if (field.default_val.tag() == .unreachable_value)
- null
- else
- field.default_val;
- const default_val_ptr = try sema.optRefValue(block, src, field.ty, opt_default_val);
- const alignment = switch (layout) {
- .Auto, .Extern => field.normalAlignment(target),
- .Packed => field.packedAlignment(),
- };
+ const struct_field_fields = try fields_anon_decl.arena().create([5]Value);
+ const field_val = payload.data.values[i];
+ const is_comptime = field_val.tag() != .unreachable_value;
+ const opt_default_val = if (is_comptime) field_val else null;
+ const default_val_ptr = try sema.optRefValue(block, src, field_ty, opt_default_val);
+ const alignment = field_ty.abiAlignment(target);
+
+ struct_field_fields.* = .{
+ // name: []const u8,
+ name_val,
+ // field_type: type,
+ try Value.Tag.ty.create(fields_anon_decl.arena(), field_ty),
+ // default_value: ?*const anyopaque,
+ try default_val_ptr.copy(fields_anon_decl.arena()),
+ // is_comptime: bool,
+ Value.makeBool(is_comptime),
+ // alignment: comptime_int,
+ try Value.Tag.int_u64.create(fields_anon_decl.arena(), alignment),
+ };
+ struct_field_val.* = try Value.Tag.@"struct".create(fields_anon_decl.arena(), struct_field_fields);
+ }
+ break :fv struct_field_vals;
+ }
+ const struct_fields = struct_ty.structFields();
+ const struct_field_vals = try fields_anon_decl.arena().alloc(Value, struct_fields.count());
+
+ for (struct_field_vals) |*field_val, i| {
+ const field = struct_fields.values()[i];
+ const name = struct_fields.keys()[i];
+ const name_val = v: {
+ var anon_decl = try block.startAnonDecl(src);
+ defer anon_decl.deinit();
+ const bytes = try anon_decl.arena().dupeZ(u8, name);
+ const new_decl = try anon_decl.finish(
+ try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len),
+ try Value.Tag.bytes.create(anon_decl.arena(), bytes[0 .. bytes.len + 1]),
+ );
+ break :v try Value.Tag.decl_ref.create(fields_anon_decl.arena(), new_decl);
+ };
- struct_field_fields.* = .{
- // name: []const u8,
- name_val,
- // field_type: type,
- try Value.Tag.ty.create(fields_anon_decl.arena(), field.ty),
- // default_value: ?*const anyopaque,
- try default_val_ptr.copy(fields_anon_decl.arena()),
- // is_comptime: bool,
- Value.makeBool(field.is_comptime),
- // alignment: comptime_int,
- try Value.Tag.int_u64.create(fields_anon_decl.arena(), alignment),
- };
- field_val.* = try Value.Tag.@"struct".create(fields_anon_decl.arena(), struct_field_fields);
- }
+ const struct_field_fields = try fields_anon_decl.arena().create([5]Value);
+ const opt_default_val = if (field.default_val.tag() == .unreachable_value)
+ null
+ else
+ field.default_val;
+ const default_val_ptr = try sema.optRefValue(block, src, field.ty, opt_default_val);
+ const alignment = switch (layout) {
+ .Auto, .Extern => field.normalAlignment(target),
+ .Packed => field.packedAlignment(),
+ };
+
+ struct_field_fields.* = .{
+ // name: []const u8,
+ name_val,
+ // field_type: type,
+ try Value.Tag.ty.create(fields_anon_decl.arena(), field.ty),
+ // default_value: ?*const anyopaque,
+ try default_val_ptr.copy(fields_anon_decl.arena()),
+ // is_comptime: bool,
+ Value.makeBool(field.is_comptime),
+ // alignment: comptime_int,
+ try Value.Tag.int_u64.create(fields_anon_decl.arena(), alignment),
+ };
+ field_val.* = try Value.Tag.@"struct".create(fields_anon_decl.arena(), struct_field_fields);
+ }
+ break :fv struct_field_vals;
+ };
const fields_val = v: {
const new_decl = try fields_anon_decl.finish(
src/type.zig
@@ -2031,21 +2031,21 @@ pub const Type = extern union {
.empty_struct,
.void,
.anyopaque,
- => return 0,
-
.empty_struct_literal,
.type,
.comptime_int,
.comptime_float,
- .noreturn,
.@"null",
.@"undefined",
.enum_literal,
+ .type_info,
+ => return 0,
+
+ .noreturn,
.inferred_alloc_const,
.inferred_alloc_mut,
.@"opaque",
.var_args_param,
- .type_info,
.bound_fn,
=> unreachable,
@@ -4782,6 +4782,7 @@ pub const Type = extern union {
base: Payload = .{ .tag = .tuple },
data: struct {
types: []Type,
+ /// unreachable_value elements are used to indicate runtime-known.
values: []Value,
},
};
test/behavior/type_info.zig
@@ -454,10 +454,13 @@ test "Declarations are returned in declaration order" {
try expect(std.mem.eql(u8, d[4].name, "e"));
}
-test "Struct.is_tuple" {
+test "Struct.is_tuple for anon list literal" {
+ try expect(@typeInfo(@TypeOf(.{0})).Struct.is_tuple);
+}
+
+test "Struct.is_tuple for anon struct literal" {
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
- try expect(@typeInfo(@TypeOf(.{0})).Struct.is_tuple);
try expect(!@typeInfo(@TypeOf(.{ .a = 0 })).Struct.is_tuple);
}