diff options
| author | Andrew Kelley <andrew@ziglang.org> | 2021-03-12 18:05:27 -0700 |
|---|---|---|
| committer | Andrew Kelley <andrew@ziglang.org> | 2021-03-12 18:05:27 -0700 |
| commit | 1f34c03ac14ac352ec03267ca8592dadfbd5e4bc (patch) | |
| tree | ebcb851922636b7dd2b17acb72187836c86180ec /src/type.zig | |
| parent | 868253a9c94d9907fae81e5e3108c7d10a85f5c3 (diff) | |
| parent | 8ebb18d9da0bfbe6a974636fd36e3391d1de253b (diff) | |
| download | zig-1f34c03ac14ac352ec03267ca8592dadfbd5e4bc.tar.gz zig-1f34c03ac14ac352ec03267ca8592dadfbd5e4bc.zip | |
Merge remote-tracking branch 'origin/master' into llvm12
Diffstat (limited to 'src/type.zig')
| -rw-r--r-- | src/type.zig | 72 |
1 files changed, 70 insertions, 2 deletions
diff --git a/src/type.zig b/src/type.zig index 30605ce67b..ecdf0d333a 100644 --- a/src/type.zig +++ b/src/type.zig @@ -97,6 +97,8 @@ pub const Type = extern union { .@"struct", .empty_struct => return .Struct, .@"enum" => return .Enum, .@"union" => return .Union, + + .var_args_param => unreachable, // can be any type } } @@ -258,6 +260,8 @@ pub const Type = extern union { if (!a.fnParamType(i).eql(b.fnParamType(i))) return false; } + if (a.fnIsVarArgs() != b.fnIsVarArgs()) + return false; return true; }, .Optional => { @@ -323,6 +327,7 @@ pub const Type = extern union { while (i < params_len) : (i += 1) { std.hash.autoHash(&hasher, self.fnParamType(i).hash()); } + std.hash.autoHash(&hasher, self.fnIsVarArgs()); }, .Optional => { var buf: Payload.ElemType = undefined; @@ -397,6 +402,7 @@ pub const Type = extern union { .@"anyframe", .inferred_alloc_const, .inferred_alloc_mut, + .var_args_param, => unreachable, .array_u8, @@ -446,6 +452,7 @@ pub const Type = extern union { .return_type = try payload.return_type.copy(allocator), .param_types = param_types, .cc = payload.cc, + .is_var_args = payload.is_var_args, }); }, .pointer => { @@ -535,6 +542,7 @@ pub const Type = extern union { .comptime_int, .comptime_float, .noreturn, + .var_args_param, => return out_stream.writeAll(@tagName(t)), .enum_literal => return out_stream.writeAll("@Type(.EnumLiteral)"), @@ -558,6 +566,12 @@ pub const Type = extern union { if (i != 0) try out_stream.writeAll(", "); try param_type.format("", .{}, out_stream); } + if (payload.is_var_args) { + if (payload.param_types.len != 0) { + try out_stream.writeAll(", "); + } + try out_stream.writeAll("..."); + } try out_stream.writeAll(") callconv(."); try out_stream.writeAll(@tagName(payload.cc)); try out_stream.writeAll(")"); @@ -844,6 +858,7 @@ pub const Type = extern union { .inferred_alloc_const => unreachable, .inferred_alloc_mut => unreachable, + .var_args_param => unreachable, }; } @@ -969,6 +984,7 @@ pub const Type = extern union { .inferred_alloc_const, .inferred_alloc_mut, .@"opaque", + .var_args_param, => unreachable, }; } @@ -995,6 +1011,7 @@ pub const Type = extern union { .inferred_alloc_const => unreachable, .inferred_alloc_mut => unreachable, .@"opaque" => unreachable, + .var_args_param => unreachable, .u8, .i8, @@ -1179,6 +1196,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => false, .single_const_pointer, @@ -1256,6 +1274,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => unreachable, .const_slice, @@ -1354,6 +1373,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => false, .const_slice, @@ -1434,6 +1454,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => false, .single_const_pointer, @@ -1523,6 +1544,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => false, .pointer => { @@ -1607,6 +1629,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => false, .pointer => { @@ -1663,8 +1686,8 @@ pub const Type = extern union { return ty.optionalChild(&buf).isValidVarType(is_extern); }, .Pointer, .Array => ty = ty.elemType(), + .ErrorUnion => ty = ty.errorUnionChild(), - .ErrorUnion => @panic("TODO fn isValidVarType"), .Fn => @panic("TODO fn isValidVarType"), .Struct => @panic("TODO struct isValidVarType"), .Union => @panic("TODO union isValidVarType"), @@ -1733,6 +1756,7 @@ pub const Type = extern union { .@"struct" => unreachable, .@"union" => unreachable, .@"opaque" => unreachable, + .var_args_param => unreachable, .array => self.castTag(.array).?.data.elem_type, .array_sentinel => self.castTag(.array_sentinel).?.data.elem_type, @@ -1789,6 +1813,29 @@ pub const Type = extern union { } } + /// Asserts that the type is an error union. + pub fn errorUnionChild(self: Type) Type { + return switch (self.tag()) { + .anyerror_void_error_union => Type.initTag(.anyerror), + .error_union => { + const payload = self.castTag(.error_union).?; + return payload.data.payload; + }, + else => unreachable, + }; + } + + pub fn errorUnionSet(self: Type) Type { + return switch (self.tag()) { + .anyerror_void_error_union => Type.initTag(.anyerror), + .error_union => { + const payload = self.castTag(.error_union).?; + return payload.data.error_set; + }, + else => unreachable, + }; + } + /// Asserts the type is an array or vector. pub fn arrayLen(self: Type) u64 { return switch (self.tag()) { @@ -1862,6 +1909,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => unreachable, .array => self.castTag(.array).?.data.len, @@ -1936,6 +1984,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => unreachable, .single_const_pointer, @@ -2025,6 +2074,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => false, .int_signed, @@ -2110,6 +2160,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => false, .int_unsigned, @@ -2181,6 +2232,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => unreachable, .int_unsigned => .{ @@ -2280,6 +2332,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => false, .usize, @@ -2400,6 +2453,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => unreachable, }; } @@ -2486,6 +2540,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => unreachable, } } @@ -2571,6 +2626,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => unreachable, } } @@ -2656,6 +2712,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => unreachable, }; } @@ -2738,6 +2795,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => unreachable, }; } @@ -2749,7 +2807,7 @@ pub const Type = extern union { .fn_void_no_args => false, .fn_naked_noreturn_no_args => false, .fn_ccc_void_no_args => false, - .function => false, + .function => self.castTag(.function).?.data.is_var_args, .f16, .f32, @@ -2820,6 +2878,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => unreachable, }; } @@ -2902,6 +2961,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => false, }; } @@ -2962,6 +3022,7 @@ pub const Type = extern union { .error_set, .error_set_single, .@"opaque", + .var_args_param, => return null, .@"enum" => @panic("TODO onePossibleValue enum"), @@ -3079,6 +3140,7 @@ pub const Type = extern union { .@"struct", .@"union", .@"opaque", + .var_args_param, => return false, .c_const_pointer, @@ -3168,6 +3230,7 @@ pub const Type = extern union { .pointer, .inferred_alloc_const, .inferred_alloc_mut, + .var_args_param, => unreachable, .empty_struct => self.castTag(.empty_struct).?.data, @@ -3285,6 +3348,9 @@ pub const Type = extern union { anyerror_void_error_union, @"anyframe", const_slice_u8, + /// This is a special type for variadic parameters of a function call. + /// Casts to it will validate that the type can be passed to a c calling convetion function. + var_args_param, /// This is a special value that tracks a set of types that have been stored /// to an inferred allocation. It does not support most of the normal type queries. /// However it does respond to `isConstPtr`, `ptrSize`, `zigTypeTag`, etc. @@ -3373,6 +3439,7 @@ pub const Type = extern union { .const_slice_u8, .inferred_alloc_const, .inferred_alloc_mut, + .var_args_param, => @compileError("Type Tag " ++ @tagName(t) ++ " has no payload"), .array_u8, @@ -3479,6 +3546,7 @@ pub const Type = extern union { param_types: []Type, return_type: Type, cc: std.builtin.CallingConvention, + is_var_args: bool, }, }; |
