Lots of 0.14 changes

This commit is contained in:
Mitchell Hashimoto
2025-03-12 09:55:46 -07:00
parent 86d3f18707
commit 0f4d2bb237
67 changed files with 326 additions and 316 deletions

View File

@@ -119,7 +119,7 @@ pub const Action = enum {
// If help is requested, then we use some comptime trickery
// to find this action in the help strings and output that.
help_error => err: {
inline for (@typeInfo(Action).Enum.fields) |field| {
inline for (@typeInfo(Action).@"enum".fields) |field| {
// Future note: for now we just output the help text directly
// to stdout. In the future we can style this much prettier
// for all commands by just changing this one place.

View File

@@ -55,7 +55,7 @@ pub fn parse(
iter: anytype,
) !void {
const info = @typeInfo(T);
assert(info == .Struct);
assert(info == .@"struct");
comptime {
// Verify all renamed fields are valid (source does not exist,
@@ -208,10 +208,10 @@ fn formatInvalidValue(
fn formatValues(comptime T: type, key: []const u8, writer: anytype) std.mem.Allocator.Error!void {
const typeinfo = @typeInfo(T);
inline for (typeinfo.Struct.fields) |f| {
inline for (typeinfo.@"struct".fields) |f| {
if (std.mem.eql(u8, key, f.name)) {
switch (@typeInfo(f.type)) {
.Enum => |e| {
.@"enum" => |e| {
try writer.print(", valid values are: ", .{});
inline for (e.fields, 0..) |field, i| {
if (i != 0) try writer.print(", ", .{});
@@ -243,19 +243,21 @@ pub fn parseIntoField(
value: ?[]const u8,
) !void {
const info = @typeInfo(T);
assert(info == .Struct);
assert(info == .@"struct");
inline for (info.Struct.fields) |field| {
inline for (info.@"struct".fields) |field| {
if (field.name[0] != '_' and mem.eql(u8, field.name, key)) {
// For optional fields, we just treat it as the child type.
// This lets optional fields default to null but get set by
// the CLI.
const Field = switch (@typeInfo(field.type)) {
.Optional => |opt| opt.child,
.optional => |opt| opt.child,
else => field.type,
};
const fieldInfo = @typeInfo(Field);
const canHaveDecls = fieldInfo == .Struct or fieldInfo == .Union or fieldInfo == .Enum;
const canHaveDecls = fieldInfo == .@"struct" or
fieldInfo == .@"union" or
fieldInfo == .@"enum";
// If the value is empty string (set but empty string),
// then we reset the value to the default.
@@ -266,7 +268,7 @@ pub fn parseIntoField(
try @field(dst, field.name).init(alloc);
return;
}
const raw = field.default_value orelse break :default;
const raw = field.default_value_ptr orelse break :default;
const ptr: *const field.type = @alignCast(@ptrCast(raw));
@field(dst, field.name) = ptr.*;
return;
@@ -276,22 +278,22 @@ pub fn parseIntoField(
// we call that and use that to set the value.
if (canHaveDecls) {
if (@hasDecl(Field, "parseCLI")) {
const fnInfo = @typeInfo(@TypeOf(Field.parseCLI)).Fn;
const fnInfo = @typeInfo(@TypeOf(Field.parseCLI)).@"fn";
switch (fnInfo.params.len) {
// 1 arg = (input) => output
1 => @field(dst, field.name) = try Field.parseCLI(value),
// 2 arg = (self, input) => void
2 => switch (@typeInfo(field.type)) {
.Struct,
.Union,
.Enum,
.@"struct",
.@"union",
.@"enum",
=> try @field(dst, field.name).parseCLI(value),
// If the field is optional and set, then we use
// the pointer value directly into it. If its not
// set we need to create a new instance.
.Optional => if (@field(dst, field.name)) |*v| {
.optional => if (@field(dst, field.name)) |*v| {
try v.parseCLI(value);
} else {
// Note: you cannot do @field(dst, name) = undefined
@@ -307,12 +309,12 @@ pub fn parseIntoField(
// 3 arg = (self, alloc, input) => void
3 => switch (@typeInfo(field.type)) {
.Struct,
.Union,
.Enum,
.@"struct",
.@"union",
.@"enum",
=> try @field(dst, field.name).parseCLI(alloc, value),
.Optional => if (@field(dst, field.name)) |*v| {
.optional => if (@field(dst, field.name)) |*v| {
try v.parseCLI(alloc, value);
} else {
var tmp: Field = undefined;
@@ -374,18 +376,18 @@ pub fn parseIntoField(
) catch return error.InvalidValue,
else => switch (fieldInfo) {
.Enum => std.meta.stringToEnum(
.@"enum" => std.meta.stringToEnum(
Field,
value orelse return error.ValueRequired,
) orelse return error.InvalidValue,
.Struct => try parseStruct(
.@"struct" => try parseStruct(
Field,
alloc,
value orelse return error.ValueRequired,
),
.Union => try parseTaggedUnion(
.@"union" => try parseTaggedUnion(
Field,
alloc,
value orelse return error.ValueRequired,
@@ -413,8 +415,8 @@ pub fn parseIntoField(
}
fn parseTaggedUnion(comptime T: type, alloc: Allocator, v: []const u8) !T {
const info = @typeInfo(T).Union;
assert(@typeInfo(info.tag_type.?) == .Enum);
const info = @typeInfo(T).@"union";
assert(@typeInfo(info.tag_type.?) == .@"enum");
// Get the union tag that is being set. We support values with no colon
// if the value is void so its not an error to have no colon.
@@ -433,12 +435,12 @@ fn parseTaggedUnion(comptime T: type, alloc: Allocator, v: []const u8) !T {
// We need to create a struct that looks like this union field.
// This lets us use parseIntoField as if its a dedicated struct.
const Target = @Type(.{ .Struct = .{
const Target = @Type(.{ .@"struct" = .{
.layout = .auto,
.fields = &.{.{
.name = field.name,
.type = field.type,
.default_value = null,
.default_value_ptr = null,
.is_comptime = false,
.alignment = @alignOf(field.type),
}},
@@ -459,7 +461,7 @@ fn parseTaggedUnion(comptime T: type, alloc: Allocator, v: []const u8) !T {
}
fn parseStruct(comptime T: type, alloc: Allocator, v: []const u8) !T {
return switch (@typeInfo(T).Struct.layout) {
return switch (@typeInfo(T).@"struct".layout) {
.auto => parseAutoStruct(T, alloc, v),
.@"packed" => parsePackedStruct(T, v),
else => @compileError("unsupported struct layout"),
@@ -467,7 +469,7 @@ fn parseStruct(comptime T: type, alloc: Allocator, v: []const u8) !T {
}
pub fn parseAutoStruct(comptime T: type, alloc: Allocator, v: []const u8) !T {
const info = @typeInfo(T).Struct;
const info = @typeInfo(T).@"struct";
comptime assert(info.layout == .auto);
// We start our result as undefined so we don't get an error for required
@@ -519,7 +521,7 @@ pub fn parseAutoStruct(comptime T: type, alloc: Allocator, v: []const u8) !T {
// Ensure all required fields are set
inline for (info.fields, 0..) |field, i| {
if (!fields_set.isSet(i)) {
const default_ptr = field.default_value orelse return error.InvalidValue;
const default_ptr = field.default_value_ptr orelse return error.InvalidValue;
const typed_ptr: *const field.type = @alignCast(@ptrCast(default_ptr));
@field(result, field.name) = typed_ptr.*;
}
@@ -529,7 +531,7 @@ pub fn parseAutoStruct(comptime T: type, alloc: Allocator, v: []const u8) !T {
}
fn parsePackedStruct(comptime T: type, v: []const u8) !T {
const info = @typeInfo(T).Struct;
const info = @typeInfo(T).@"struct";
comptime assert(info.layout == .@"packed");
var result: T = .{};

View File

@@ -54,14 +54,14 @@ pub const Location = union(enum) {
line: usize,
},
pub const Key = @typeInfo(Location).Union.tag_type.?;
pub const Key = @typeInfo(Location).@"union".tag_type.?;
pub fn fromIter(iter: anytype, alloc: Allocator) Allocator.Error!Location {
const Iter = t: {
const T = @TypeOf(iter);
break :t switch (@typeInfo(T)) {
.Pointer => |v| v.child,
.Struct => T,
.pointer => |v| v.child,
.@"struct" => T,
else => return .none,
};
};

View File

@@ -58,7 +58,7 @@ pub fn run(alloc: Allocator) !u8 {
\\
);
inline for (@typeInfo(Action).Enum.fields) |field| {
inline for (@typeInfo(Action).@"enum".fields) |field| {
try stdout.print(" +{s}\n", .{field.name});
}

View File

@@ -101,7 +101,7 @@ fn runArgs(alloc_gpa: Allocator, argsIter: anytype) !u8 {
var exit: bool = false;
outer: for (opts._diagnostics.items()) |diagnostic| {
if (diagnostic.location != .cli) continue :outer;
inner: inline for (@typeInfo(Options).Struct.fields) |field| {
inner: inline for (@typeInfo(Options).@"struct".fields) |field| {
if (field.name[0] == '_') continue :inner;
if (std.mem.eql(u8, field.name, diagnostic.key)) {
try stderr.writeAll("config error: ");
@@ -134,7 +134,7 @@ fn runArgs(alloc_gpa: Allocator, argsIter: anytype) !u8 {
// action-specific argument.
if (!config._diagnostics.empty()) {
outer: for (config._diagnostics.items()) |diagnostic| {
inner: inline for (@typeInfo(Options).Struct.fields) |field| {
inner: inline for (@typeInfo(Options).@"struct".fields) |field| {
if (field.name[0] == '_') continue :inner;
if (std.mem.eql(u8, field.name, diagnostic.key) and (diagnostic.location == .none or diagnostic.location == .cli)) continue :outer;
}