Merge pull request #23340 from castholm/pass-null-to-b-dependency
Add support for passing null, string literals, enum lists and more to `b.dependency()`
This commit is contained in:
@@ -408,104 +408,179 @@ fn createChildOnly(
|
||||
return child;
|
||||
}
|
||||
|
||||
fn userInputOptionsFromArgs(allocator: Allocator, args: anytype) UserInputOptionsMap {
|
||||
var user_input_options = UserInputOptionsMap.init(allocator);
|
||||
fn userInputOptionsFromArgs(arena: Allocator, args: anytype) UserInputOptionsMap {
|
||||
var map = UserInputOptionsMap.init(arena);
|
||||
inline for (@typeInfo(@TypeOf(args)).@"struct".fields) |field| {
|
||||
const v = @field(args, field.name);
|
||||
const T = @TypeOf(v);
|
||||
switch (T) {
|
||||
Target.Query => {
|
||||
user_input_options.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = v.zigTriple(allocator) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
user_input_options.put("cpu", .{
|
||||
.name = "cpu",
|
||||
.value = .{ .scalar = v.serializeCpuAlloc(allocator) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
ResolvedTarget => {
|
||||
user_input_options.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = v.query.zigTriple(allocator) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
user_input_options.put("cpu", .{
|
||||
.name = "cpu",
|
||||
.value = .{ .scalar = v.query.serializeCpuAlloc(allocator) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
LazyPath => {
|
||||
user_input_options.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .lazy_path = v.dupeInner(allocator) },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
[]const LazyPath => {
|
||||
var list = ArrayList(LazyPath).initCapacity(allocator, v.len) catch @panic("OOM");
|
||||
for (v) |lp| list.appendAssumeCapacity(lp.dupeInner(allocator));
|
||||
user_input_options.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .lazy_path_list = list },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
[]const u8 => {
|
||||
user_input_options.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = v },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
[]const []const u8 => {
|
||||
var list = ArrayList([]const u8).initCapacity(allocator, v.len) catch @panic("OOM");
|
||||
list.appendSliceAssumeCapacity(v);
|
||||
|
||||
user_input_options.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .list = list },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
else => switch (@typeInfo(T)) {
|
||||
.bool => {
|
||||
user_input_options.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = if (v) "true" else "false" },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
.@"enum", .enum_literal => {
|
||||
user_input_options.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = @tagName(v) },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
.comptime_int, .int => {
|
||||
user_input_options.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = std.fmt.allocPrint(allocator, "{d}", .{v}) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
.comptime_float, .float => {
|
||||
user_input_options.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = std.fmt.allocPrint(allocator, "{e}", .{v}) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
else => @compileError("option '" ++ field.name ++ "' has unsupported type: " ++ @typeName(T)),
|
||||
},
|
||||
}
|
||||
if (field.type == @Type(.null)) continue;
|
||||
addUserInputOptionFromArg(arena, &map, field, field.type, @field(args, field.name));
|
||||
}
|
||||
return map;
|
||||
}
|
||||
|
||||
return user_input_options;
|
||||
fn addUserInputOptionFromArg(
|
||||
arena: Allocator,
|
||||
map: *UserInputOptionsMap,
|
||||
field: std.builtin.Type.StructField,
|
||||
comptime T: type,
|
||||
/// If null, the value won't be added, but `T` will still be type-checked.
|
||||
maybe_value: ?T,
|
||||
) void {
|
||||
switch (T) {
|
||||
Target.Query => return if (maybe_value) |v| {
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = v.zigTriple(arena) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
map.put("cpu", .{
|
||||
.name = "cpu",
|
||||
.value = .{ .scalar = v.serializeCpuAlloc(arena) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
ResolvedTarget => return if (maybe_value) |v| {
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = v.query.zigTriple(arena) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
map.put("cpu", .{
|
||||
.name = "cpu",
|
||||
.value = .{ .scalar = v.query.serializeCpuAlloc(arena) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
std.zig.BuildId => return if (maybe_value) |v| {
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = std.fmt.allocPrint(arena, "{f}", .{v}) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
LazyPath => return if (maybe_value) |v| {
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .lazy_path = v.dupeInner(arena) },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
[]const LazyPath => return if (maybe_value) |v| {
|
||||
var list = ArrayList(LazyPath).initCapacity(arena, v.len) catch @panic("OOM");
|
||||
for (v) |lp| list.appendAssumeCapacity(lp.dupeInner(arena));
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .lazy_path_list = list },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
[]const u8 => return if (maybe_value) |v| {
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = arena.dupe(u8, v) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
[]const []const u8 => return if (maybe_value) |v| {
|
||||
var list = ArrayList([]const u8).initCapacity(arena, v.len) catch @panic("OOM");
|
||||
for (v) |s| list.appendAssumeCapacity(arena.dupe(u8, s) catch @panic("OOM"));
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .list = list },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
else => switch (@typeInfo(T)) {
|
||||
.bool => return if (maybe_value) |v| {
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = if (v) "true" else "false" },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
.@"enum", .enum_literal => return if (maybe_value) |v| {
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = @tagName(v) },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
.comptime_int, .int => return if (maybe_value) |v| {
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = std.fmt.allocPrint(arena, "{d}", .{v}) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
.comptime_float, .float => return if (maybe_value) |v| {
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .scalar = std.fmt.allocPrint(arena, "{x}", .{v}) catch @panic("OOM") },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
.pointer => |ptr_info| switch (ptr_info.size) {
|
||||
.one => switch (@typeInfo(ptr_info.child)) {
|
||||
.array => |array_info| {
|
||||
comptime var slice_info = ptr_info;
|
||||
slice_info.size = .slice;
|
||||
slice_info.is_const = true;
|
||||
slice_info.child = array_info.child;
|
||||
slice_info.sentinel_ptr = null;
|
||||
addUserInputOptionFromArg(
|
||||
arena,
|
||||
map,
|
||||
field,
|
||||
@Type(.{ .pointer = slice_info }),
|
||||
maybe_value orelse null,
|
||||
);
|
||||
return;
|
||||
},
|
||||
else => {},
|
||||
},
|
||||
.slice => switch (@typeInfo(ptr_info.child)) {
|
||||
.@"enum" => return if (maybe_value) |v| {
|
||||
var list = ArrayList([]const u8).initCapacity(arena, v.len) catch @panic("OOM");
|
||||
for (v) |tag| list.appendAssumeCapacity(@tagName(tag));
|
||||
map.put(field.name, .{
|
||||
.name = field.name,
|
||||
.value = .{ .list = list },
|
||||
.used = false,
|
||||
}) catch @panic("OOM");
|
||||
},
|
||||
else => {
|
||||
comptime var slice_info = ptr_info;
|
||||
slice_info.is_const = true;
|
||||
slice_info.sentinel_ptr = null;
|
||||
addUserInputOptionFromArg(
|
||||
arena,
|
||||
map,
|
||||
field,
|
||||
@Type(.{ .pointer = slice_info }),
|
||||
maybe_value orelse null,
|
||||
);
|
||||
return;
|
||||
},
|
||||
},
|
||||
else => {},
|
||||
},
|
||||
.null => unreachable,
|
||||
.optional => |info| switch (@typeInfo(info.child)) {
|
||||
.optional => {},
|
||||
else => {
|
||||
addUserInputOptionFromArg(
|
||||
arena,
|
||||
map,
|
||||
field,
|
||||
info.child,
|
||||
maybe_value orelse null,
|
||||
);
|
||||
return;
|
||||
},
|
||||
},
|
||||
else => {},
|
||||
},
|
||||
}
|
||||
@compileError("option '" ++ field.name ++ "' has unsupported type: " ++ @typeName(field.type));
|
||||
}
|
||||
|
||||
const OrderedUserValue = union(enum) {
|
||||
|
||||
@@ -1564,17 +1564,23 @@ pub fn printFloatHexOptions(w: *Writer, value: anytype, options: std.fmt.Number)
|
||||
}
|
||||
|
||||
pub fn printFloatHex(w: *Writer, value: anytype, case: std.fmt.Case, opt_precision: ?usize) Error!void {
|
||||
if (std.math.signbit(value)) try w.writeByte('-');
|
||||
if (std.math.isNan(value)) return w.writeAll(switch (case) {
|
||||
const v = switch (@TypeOf(value)) {
|
||||
// comptime_float internally is a f128; this preserves precision.
|
||||
comptime_float => @as(f128, value),
|
||||
else => value,
|
||||
};
|
||||
|
||||
if (std.math.signbit(v)) try w.writeByte('-');
|
||||
if (std.math.isNan(v)) return w.writeAll(switch (case) {
|
||||
.lower => "nan",
|
||||
.upper => "NAN",
|
||||
});
|
||||
if (std.math.isInf(value)) return w.writeAll(switch (case) {
|
||||
if (std.math.isInf(v)) return w.writeAll(switch (case) {
|
||||
.lower => "inf",
|
||||
.upper => "INF",
|
||||
});
|
||||
|
||||
const T = @TypeOf(value);
|
||||
const T = @TypeOf(v);
|
||||
const TU = std.meta.Int(.unsigned, @bitSizeOf(T));
|
||||
|
||||
const mantissa_bits = std.math.floatMantissaBits(T);
|
||||
@@ -1584,7 +1590,7 @@ pub fn printFloatHex(w: *Writer, value: anytype, case: std.fmt.Case, opt_precisi
|
||||
const exponent_mask = (1 << exponent_bits) - 1;
|
||||
const exponent_bias = (1 << (exponent_bits - 1)) - 1;
|
||||
|
||||
const as_bits: TU = @bitCast(value);
|
||||
const as_bits: TU = @bitCast(v);
|
||||
var mantissa = as_bits & mantissa_mask;
|
||||
var exponent: i32 = @as(u16, @truncate((as_bits >> mantissa_bits) & exponent_mask));
|
||||
|
||||
|
||||
@@ -321,6 +321,27 @@ pub const BuildId = union(enum) {
|
||||
try std.testing.expectError(error.InvalidCharacter, parse("0xfoobbb"));
|
||||
try std.testing.expectError(error.InvalidBuildIdStyle, parse("yaddaxxx"));
|
||||
}
|
||||
|
||||
pub fn format(id: BuildId, writer: *std.io.Writer) std.io.Writer.Error!void {
|
||||
switch (id) {
|
||||
.none, .fast, .uuid, .sha1, .md5 => {
|
||||
try writer.writeAll(@tagName(id));
|
||||
},
|
||||
.hexstring => |hs| {
|
||||
try writer.print("0x{x}", .{hs.toSlice()});
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
test format {
|
||||
try std.testing.expectFmt("none", "{f}", .{@as(BuildId, .none)});
|
||||
try std.testing.expectFmt("fast", "{f}", .{@as(BuildId, .fast)});
|
||||
try std.testing.expectFmt("uuid", "{f}", .{@as(BuildId, .uuid)});
|
||||
try std.testing.expectFmt("sha1", "{f}", .{@as(BuildId, .sha1)});
|
||||
try std.testing.expectFmt("md5", "{f}", .{@as(BuildId, .md5)});
|
||||
try std.testing.expectFmt("0x", "{f}", .{BuildId.initHexString("")});
|
||||
try std.testing.expectFmt("0x1234cdef", "{f}", .{BuildId.initHexString("\x12\x34\xcd\xef")});
|
||||
}
|
||||
};
|
||||
|
||||
pub const LtoMode = enum { none, full, thin };
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
.{
|
||||
.name = "link_test_cases",
|
||||
.name = .link_test_cases,
|
||||
.fingerprint = 0x404f657576fec9f2,
|
||||
.version = "0.0.0",
|
||||
.dependencies = .{
|
||||
.bss = .{
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
.{
|
||||
.name = .standalone_test_cases,
|
||||
.fingerprint = 0xc0dbdf9c818957be,
|
||||
.fingerprint = 0xc0dbdf9c3b92810b,
|
||||
.version = "0.0.0",
|
||||
.dependencies = .{
|
||||
.simple = .{
|
||||
@@ -181,6 +181,9 @@
|
||||
.install_headers = .{
|
||||
.path = "install_headers",
|
||||
},
|
||||
.dependency_options = .{
|
||||
.path = "dependency_options",
|
||||
},
|
||||
.dependencyFromBuildZig = .{
|
||||
.path = "dependencyFromBuildZig",
|
||||
},
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
.{
|
||||
.name = "dependencyFromBuildZig",
|
||||
.name = .dependencyFromBuildZig,
|
||||
.fingerprint = 0xfd939a1eb8169080,
|
||||
.version = "0.0.0",
|
||||
.dependencies = .{
|
||||
.other = .{
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
.{
|
||||
.name = "other",
|
||||
.name = .other,
|
||||
.fingerprint = 0xd9583520a2405f6c,
|
||||
.version = "0.0.0",
|
||||
.dependencies = .{},
|
||||
.paths = .{""},
|
||||
|
||||
141
test/standalone/dependency_options/build.zig
Normal file
141
test/standalone/dependency_options/build.zig
Normal file
@@ -0,0 +1,141 @@
|
||||
const std = @import("std");
|
||||
|
||||
pub const Enum = enum { alfa, bravo, charlie };
|
||||
|
||||
pub fn build(b: *std.Build) !void {
|
||||
const test_step = b.step("test", "Test passing options to a dependency");
|
||||
b.default_step = test_step;
|
||||
|
||||
const none_specified = b.dependency("other", .{});
|
||||
|
||||
const none_specified_mod = none_specified.module("dummy");
|
||||
if (!none_specified_mod.resolved_target.?.query.eql(b.graph.host.query)) return error.TestFailed;
|
||||
if (none_specified_mod.optimize.? != .Debug) return error.TestFailed;
|
||||
|
||||
// Passing null is the same as not specifying the option,
|
||||
// so this should resolve to the same cached dependency instance.
|
||||
const null_specified = b.dependency("other", .{
|
||||
// Null literals
|
||||
.target = null,
|
||||
.optimize = null,
|
||||
.bool = null,
|
||||
|
||||
// Optionals
|
||||
.int = @as(?i64, null),
|
||||
.float = @as(?f64, null),
|
||||
|
||||
// Optionals of the wrong type
|
||||
.string = @as(?usize, null),
|
||||
.@"enum" = @as(?bool, null),
|
||||
|
||||
// Non-defined option names
|
||||
.this_option_does_not_exist = null,
|
||||
.neither_does_this_one = @as(?[]const u8, null),
|
||||
});
|
||||
|
||||
if (null_specified != none_specified) return error.TestFailed;
|
||||
|
||||
const all_specified = b.dependency("other", .{
|
||||
.target = b.resolveTargetQuery(.{ .cpu_arch = .x86_64, .os_tag = .windows, .abi = .gnu }),
|
||||
.optimize = @as(std.builtin.OptimizeMode, .ReleaseSafe),
|
||||
.bool = @as(bool, true),
|
||||
.int = @as(i64, 123),
|
||||
.float = @as(f64, 0.5),
|
||||
.string = @as([]const u8, "abc"),
|
||||
.string_list = @as([]const []const u8, &.{ "a", "b", "c" }),
|
||||
.lazy_path = @as(std.Build.LazyPath, .{ .cwd_relative = "abc.txt" }),
|
||||
.lazy_path_list = @as([]const std.Build.LazyPath, &.{
|
||||
.{ .cwd_relative = "a.txt" },
|
||||
.{ .cwd_relative = "b.txt" },
|
||||
.{ .cwd_relative = "c.txt" },
|
||||
}),
|
||||
.@"enum" = @as(Enum, .alfa),
|
||||
.enum_list = @as([]const Enum, &.{ .alfa, .bravo, .charlie }),
|
||||
.build_id = @as(std.zig.BuildId, .uuid),
|
||||
.hex_build_id = std.zig.BuildId.initHexString("\x12\x34\xcd\xef"),
|
||||
});
|
||||
|
||||
const all_specified_mod = all_specified.module("dummy");
|
||||
if (all_specified_mod.resolved_target.?.result.cpu.arch != .x86_64) return error.TestFailed;
|
||||
if (all_specified_mod.resolved_target.?.result.os.tag != .windows) return error.TestFailed;
|
||||
if (all_specified_mod.resolved_target.?.result.abi != .gnu) return error.TestFailed;
|
||||
if (all_specified_mod.optimize.? != .ReleaseSafe) return error.TestFailed;
|
||||
|
||||
const all_specified_optional = b.dependency("other", .{
|
||||
.target = @as(?std.Build.ResolvedTarget, b.resolveTargetQuery(.{ .cpu_arch = .x86_64, .os_tag = .windows, .abi = .gnu })),
|
||||
.optimize = @as(?std.builtin.OptimizeMode, .ReleaseSafe),
|
||||
.bool = @as(?bool, true),
|
||||
.int = @as(?i64, 123),
|
||||
.float = @as(?f64, 0.5),
|
||||
.string = @as(?[]const u8, "abc"),
|
||||
.string_list = @as(?[]const []const u8, &.{ "a", "b", "c" }),
|
||||
.lazy_path = @as(?std.Build.LazyPath, .{ .cwd_relative = "abc.txt" }),
|
||||
.lazy_path_list = @as(?[]const std.Build.LazyPath, &.{
|
||||
.{ .cwd_relative = "a.txt" },
|
||||
.{ .cwd_relative = "b.txt" },
|
||||
.{ .cwd_relative = "c.txt" },
|
||||
}),
|
||||
.@"enum" = @as(?Enum, .alfa),
|
||||
.enum_list = @as(?[]const Enum, &.{ .alfa, .bravo, .charlie }),
|
||||
.build_id = @as(?std.zig.BuildId, .uuid),
|
||||
.hex_build_id = @as(?std.zig.BuildId, .initHexString("\x12\x34\xcd\xef")),
|
||||
});
|
||||
|
||||
if (all_specified_optional != all_specified) return error.TestFailed;
|
||||
|
||||
const all_specified_literal = b.dependency("other", .{
|
||||
.target = b.resolveTargetQuery(.{ .cpu_arch = .x86_64, .os_tag = .windows, .abi = .gnu }),
|
||||
.optimize = .ReleaseSafe,
|
||||
.bool = true,
|
||||
.int = 123,
|
||||
.float = 0.5,
|
||||
.string = "abc",
|
||||
.string_list = &[_][]const u8{ "a", "b", "c" },
|
||||
.lazy_path = @as(std.Build.LazyPath, .{ .cwd_relative = "abc.txt" }),
|
||||
.lazy_path_list = &[_]std.Build.LazyPath{
|
||||
.{ .cwd_relative = "a.txt" },
|
||||
.{ .cwd_relative = "b.txt" },
|
||||
.{ .cwd_relative = "c.txt" },
|
||||
},
|
||||
.@"enum" = .alfa,
|
||||
.enum_list = &[_]Enum{ .alfa, .bravo, .charlie },
|
||||
.build_id = .uuid,
|
||||
.hex_build_id = std.zig.BuildId.initHexString("\x12\x34\xcd\xef"),
|
||||
});
|
||||
|
||||
if (all_specified_literal != all_specified) return error.TestFailed;
|
||||
|
||||
var mut_string_buf = "abc".*;
|
||||
const mut_string: []u8 = &mut_string_buf;
|
||||
var mut_string_list_buf = [_][]const u8{ "a", "b", "c" };
|
||||
const mut_string_list: [][]const u8 = &mut_string_list_buf;
|
||||
var mut_lazy_path_list_buf = [_]std.Build.LazyPath{
|
||||
.{ .cwd_relative = "a.txt" },
|
||||
.{ .cwd_relative = "b.txt" },
|
||||
.{ .cwd_relative = "c.txt" },
|
||||
};
|
||||
const mut_lazy_path_list: []std.Build.LazyPath = &mut_lazy_path_list_buf;
|
||||
var mut_enum_list_buf = [_]Enum{ .alfa, .bravo, .charlie };
|
||||
const mut_enum_list: []Enum = &mut_enum_list_buf;
|
||||
|
||||
// Most supported option types are serialized to a string representation,
|
||||
// so alternative representations of the same option value should resolve
|
||||
// to the same cached dependency instance.
|
||||
const all_specified_alt = b.dependency("other", .{
|
||||
.target = @as(std.Target.Query, .{ .cpu_arch = .x86_64, .os_tag = .windows, .abi = .gnu }),
|
||||
.optimize = "ReleaseSafe",
|
||||
.bool = .true,
|
||||
.int = "123",
|
||||
.float = @as(f16, 0.5),
|
||||
.string = mut_string,
|
||||
.string_list = mut_string_list,
|
||||
.lazy_path = @as(std.Build.LazyPath, .{ .cwd_relative = "abc.txt" }),
|
||||
.lazy_path_list = mut_lazy_path_list,
|
||||
.@"enum" = "alfa",
|
||||
.enum_list = mut_enum_list,
|
||||
.build_id = "uuid",
|
||||
.hex_build_id = "0x1234cdef",
|
||||
});
|
||||
|
||||
if (all_specified_alt != all_specified) return error.TestFailed;
|
||||
}
|
||||
11
test/standalone/dependency_options/build.zig.zon
Normal file
11
test/standalone/dependency_options/build.zig.zon
Normal file
@@ -0,0 +1,11 @@
|
||||
.{
|
||||
.name = .dependency_options,
|
||||
.fingerprint = 0x3e3ce1c1f92ba47e,
|
||||
.version = "0.0.0",
|
||||
.dependencies = .{
|
||||
.other = .{
|
||||
.path = "other",
|
||||
},
|
||||
},
|
||||
.paths = .{""},
|
||||
}
|
||||
59
test/standalone/dependency_options/other/build.zig
Normal file
59
test/standalone/dependency_options/other/build.zig
Normal file
@@ -0,0 +1,59 @@
|
||||
const std = @import("std");
|
||||
|
||||
pub const Enum = enum { alfa, bravo, charlie };
|
||||
|
||||
pub fn build(b: *std.Build) !void {
|
||||
const target = b.standardTargetOptions(.{});
|
||||
const optimize = b.standardOptimizeOption(.{});
|
||||
|
||||
const expected_bool: bool = true;
|
||||
const expected_int: i64 = 123;
|
||||
const expected_float: f64 = 0.5;
|
||||
const expected_string: []const u8 = "abc";
|
||||
const expected_string_list: []const []const u8 = &.{ "a", "b", "c" };
|
||||
const expected_lazy_path: std.Build.LazyPath = .{ .cwd_relative = "abc.txt" };
|
||||
const expected_lazy_path_list: []const std.Build.LazyPath = &.{
|
||||
.{ .cwd_relative = "a.txt" },
|
||||
.{ .cwd_relative = "b.txt" },
|
||||
.{ .cwd_relative = "c.txt" },
|
||||
};
|
||||
const expected_enum: Enum = .alfa;
|
||||
const expected_enum_list: []const Enum = &.{ .alfa, .bravo, .charlie };
|
||||
const expected_build_id: std.zig.BuildId = .uuid;
|
||||
const expected_hex_build_id: std.zig.BuildId = .initHexString("\x12\x34\xcd\xef");
|
||||
|
||||
const @"bool" = b.option(bool, "bool", "bool") orelse expected_bool;
|
||||
const int = b.option(i64, "int", "int") orelse expected_int;
|
||||
const float = b.option(f64, "float", "float") orelse expected_float;
|
||||
const string = b.option([]const u8, "string", "string") orelse expected_string;
|
||||
const string_list = b.option([]const []const u8, "string_list", "string_list") orelse expected_string_list;
|
||||
const lazy_path = b.option(std.Build.LazyPath, "lazy_path", "lazy_path") orelse expected_lazy_path;
|
||||
const lazy_path_list = b.option([]const std.Build.LazyPath, "lazy_path_list", "lazy_path_list") orelse expected_lazy_path_list;
|
||||
const @"enum" = b.option(Enum, "enum", "enum") orelse expected_enum;
|
||||
const enum_list = b.option([]const Enum, "enum_list", "enum_list") orelse expected_enum_list;
|
||||
const build_id = b.option(std.zig.BuildId, "build_id", "build_id") orelse expected_build_id;
|
||||
const hex_build_id = b.option(std.zig.BuildId, "hex_build_id", "hex_build_id") orelse expected_hex_build_id;
|
||||
|
||||
if (@"bool" != expected_bool) return error.TestFailed;
|
||||
if (int != expected_int) return error.TestFailed;
|
||||
if (float != expected_float) return error.TestFailed;
|
||||
if (!std.mem.eql(u8, string, expected_string)) return error.TestFailed;
|
||||
if (string_list.len != expected_string_list.len) return error.TestFailed;
|
||||
for (string_list, expected_string_list) |x, y| {
|
||||
if (!std.mem.eql(u8, x, y)) return error.TestFailed;
|
||||
}
|
||||
if (!std.mem.eql(u8, lazy_path.cwd_relative, expected_lazy_path.cwd_relative)) return error.TestFailed;
|
||||
for (lazy_path_list, expected_lazy_path_list) |x, y| {
|
||||
if (!std.mem.eql(u8, x.cwd_relative, y.cwd_relative)) return error.TestFailed;
|
||||
}
|
||||
if (@"enum" != expected_enum) return error.TestFailed;
|
||||
if (!std.mem.eql(Enum, enum_list, expected_enum_list)) return error.TestFailed;
|
||||
if (!std.meta.eql(build_id, expected_build_id)) return error.TestFailed;
|
||||
if (!hex_build_id.eql(expected_hex_build_id)) return error.TestFailed;
|
||||
|
||||
_ = b.addModule("dummy", .{
|
||||
.root_source_file = b.path("build.zig"),
|
||||
.target = target,
|
||||
.optimize = optimize,
|
||||
});
|
||||
}
|
||||
7
test/standalone/dependency_options/other/build.zig.zon
Normal file
7
test/standalone/dependency_options/other/build.zig.zon
Normal file
@@ -0,0 +1,7 @@
|
||||
.{
|
||||
.name = .other,
|
||||
.fingerprint = 0xd95835207bc8b630,
|
||||
.version = "0.0.0",
|
||||
.dependencies = .{},
|
||||
.paths = .{""},
|
||||
}
|
||||
Reference in New Issue
Block a user