Skip to content

Commit b66b7c5

Browse files
committed
build system: implement --system [dir]
This prevents package fetching and enables system_package_mode in the build system which flips the defaults for system integrations.
1 parent 70e1b77 commit b66b7c5

File tree

4 files changed

+70
-17
lines changed

4 files changed

+70
-17
lines changed

lib/build_runner.zig

Lines changed: 17 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -202,6 +202,11 @@ pub fn main() !void {
202202
builder.debug_pkg_config = true;
203203
} else if (mem.eql(u8, arg, "--debug-compile-errors")) {
204204
builder.debug_compile_errors = true;
205+
} else if (mem.eql(u8, arg, "--system")) {
206+
// The usage text shows another argument after this parameter
207+
// but it is handled by the parent process. The build runner
208+
// only sees this flag.
209+
graph.system_package_mode = true;
205210
} else if (mem.eql(u8, arg, "--glibc-runtimes")) {
206211
builder.glibc_runtimes_dir = nextArgOrFatal(args, &arg_idx);
207212
} else if (mem.eql(u8, arg, "--verbose-link")) {
@@ -1053,18 +1058,14 @@ fn usage(b: *std.Build, out_stream: anytype) !void {
10531058
try out_stream.writeAll(
10541059
\\
10551060
\\General Options:
1056-
\\ -p, --prefix [path] Where to put installed files (default: zig-out)
1057-
\\ --prefix-lib-dir [path] Where to put installed libraries
1058-
\\ --prefix-exe-dir [path] Where to put installed executables
1059-
\\ --prefix-include-dir [path] Where to put installed C header files
1061+
\\ -p, --prefix [path] Where to install files (default: zig-out)
1062+
\\ --prefix-lib-dir [path] Where to install libraries
1063+
\\ --prefix-exe-dir [path] Where to install executables
1064+
\\ --prefix-include-dir [path] Where to install C header files
10601065
\\
10611066
\\ --release[=mode] Request release mode, optionally specifying a
10621067
\\ preferred optimization mode: fast, safe, small
10631068
\\
1064-
\\ --sysroot [path] Set the system root directory (usually /)
1065-
\\ --search-prefix [path] Add a path to look for binaries, libraries, headers
1066-
\\ --libc [file] Provide a file which specifies libc paths
1067-
\\
10681069
\\ -fdarling, -fno-darling Integration with system-installed Darling to
10691070
\\ execute macOS programs on Linux hosts
10701071
\\ (default: no)
@@ -1122,13 +1123,18 @@ fn usage(b: *std.Build, out_stream: anytype) !void {
11221123
try out_stream.writeAll(
11231124
\\
11241125
\\System Integration Options:
1125-
\\ --system [dir] System Package Mode. Disable fetching; prefer system libs
1126-
\\ -fsys=[name] Enable a system integration
1127-
\\ -fno-sys=[name] Disable a system integration
1126+
\\ --search-prefix [path] Add a path to look for binaries, libraries, headers
1127+
\\ --sysroot [path] Set the system root directory (usually /)
1128+
\\ --libc [file] Provide a file which specifies libc paths
1129+
\\
11281130
\\ --host-target [triple] Use the provided target as the host
11291131
\\ --host-cpu [cpu] Use the provided CPU as the host
11301132
\\ --host-dynamic-linker [path] Use the provided dynamic linker as the host
11311133
\\
1134+
\\ --system [pkgdir] Disable package fetching; enable all integrations
1135+
\\ -fsys=[name] Enable a system integration
1136+
\\ -fno-sys=[name] Disable a system integration
1137+
\\
11321138
\\ Available System Integrations: Enabled:
11331139
\\
11341140
);

lib/std/Build.zig

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1254,7 +1254,7 @@ pub fn standardOptimizeOption(b: *Build, options: StandardOptimizeOptionOptions)
12541254
if (b.option(
12551255
std.builtin.OptimizeMode,
12561256
"optimize",
1257-
"Prioritize performance, safety, or binary size (-O flag)",
1257+
"Prioritize performance, safety, or binary size",
12581258
)) |mode| {
12591259
return mode;
12601260
}

src/Package/Fetch.zig

Lines changed: 28 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -80,6 +80,15 @@ pub const JobQueue = struct {
8080
thread_pool: *ThreadPool,
8181
wait_group: WaitGroup = .{},
8282
global_cache: Cache.Directory,
83+
/// If true then, no fetching occurs, and:
84+
/// * The `global_cache` directory is assumed to be the direct parent
85+
/// directory of on-disk packages rather than having the "p/" directory
86+
/// prefix inside of it.
87+
/// * An error occurs if any non-lazy packages are not already present in
88+
/// the package cache directory.
89+
/// * Missing hash field causes an error, and no fetching occurs so it does
90+
/// not print the correct hash like usual.
91+
read_only: bool,
8392
recursive: bool,
8493
/// Dumps hash information to stdout which can be used to troubleshoot why
8594
/// two hashes of the same package do not match.
@@ -270,7 +279,8 @@ pub fn run(f: *Fetch) RunError!void {
270279
// We want to fail unless the resolved relative path has a
271280
// prefix of "p/$hash/".
272281
const digest_len = @typeInfo(Manifest.MultiHashHexDigest).Array.len;
273-
const expected_prefix = f.parent_package_root.sub_path[0 .. "p/".len + digest_len];
282+
const prefix_len: usize = if (f.job_queue.read_only) 0 else "p/".len;
283+
const expected_prefix = f.parent_package_root.sub_path[0 .. prefix_len + digest_len];
274284
if (!std.mem.startsWith(u8, pkg_root.sub_path, expected_prefix)) {
275285
return f.fail(
276286
f.location_tok,
@@ -311,7 +321,9 @@ pub fn run(f: *Fetch) RunError!void {
311321

312322
const s = fs.path.sep_str;
313323
if (remote.hash) |expected_hash| {
314-
const pkg_sub_path = "p" ++ s ++ expected_hash;
324+
const prefixed_pkg_sub_path = "p" ++ s ++ expected_hash;
325+
const prefix_len: usize = if (f.job_queue.read_only) "p/".len else 0;
326+
const pkg_sub_path = prefixed_pkg_sub_path[prefix_len..];
315327
if (cache_root.handle.access(pkg_sub_path, .{})) |_| {
316328
f.package_root = .{
317329
.root_dir = cache_root,
@@ -322,7 +334,14 @@ pub fn run(f: *Fetch) RunError!void {
322334
if (!f.job_queue.recursive) return;
323335
return queueJobsForDeps(f);
324336
} else |err| switch (err) {
325-
error.FileNotFound => {},
337+
error.FileNotFound => {
338+
if (f.job_queue.read_only) return f.fail(
339+
f.location_tok,
340+
try eb.printString("package not found at '{}{s}'", .{
341+
cache_root, pkg_sub_path,
342+
}),
343+
);
344+
},
326345
else => |e| {
327346
try eb.addRootErrorMessage(.{
328347
.msg = try eb.printString("unable to open global package cache directory '{}{s}': {s}", .{
@@ -332,6 +351,12 @@ pub fn run(f: *Fetch) RunError!void {
332351
return error.FetchFailed;
333352
},
334353
}
354+
} else {
355+
try eb.addRootErrorMessage(.{
356+
.msg = try eb.addString("dependency is missing hash field"),
357+
.src_loc = try f.srcLoc(f.location_tok),
358+
});
359+
return error.FetchFailed;
335360
}
336361

337362
// Fetch and unpack the remote into a temporary directory.

src/main.zig

Lines changed: 24 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5171,6 +5171,7 @@ pub fn cmdBuild(gpa: Allocator, arena: Allocator, args: []const []const u8) !voi
51715171
var verbose_cimport = false;
51725172
var verbose_llvm_cpu_features = false;
51735173
var fetch_only = false;
5174+
var system_pkg_dir_path: ?[]const u8 = null;
51745175

51755176
const argv_index_exe = child_argv.items.len;
51765177
_ = try child_argv.addOne();
@@ -5227,6 +5228,12 @@ pub fn cmdBuild(gpa: Allocator, arena: Allocator, args: []const []const u8) !voi
52275228
reference_trace = 256;
52285229
} else if (mem.eql(u8, arg, "--fetch")) {
52295230
fetch_only = true;
5231+
} else if (mem.eql(u8, arg, "--system")) {
5232+
if (i + 1 >= args.len) fatal("expected argument after '{s}'", .{arg});
5233+
i += 1;
5234+
system_pkg_dir_path = args[i];
5235+
try child_argv.append("--system");
5236+
continue;
52305237
} else if (mem.startsWith(u8, arg, "-freference-trace=")) {
52315238
const num = arg["-freference-trace=".len..];
52325239
reference_trace = std.fmt.parseUnsigned(u32, num, 10) catch |err| {
@@ -5411,8 +5418,6 @@ pub fn cmdBuild(gpa: Allocator, arena: Allocator, args: []const []const u8) !voi
54115418
var http_client: std.http.Client = .{ .allocator = gpa };
54125419
defer http_client.deinit();
54135420

5414-
try http_client.loadDefaultProxies();
5415-
54165421
var progress: std.Progress = .{ .dont_print_on_dumb = true };
54175422
const root_prog_node = progress.start("Fetch Packages", 0);
54185423
defer root_prog_node.end();
@@ -5421,12 +5426,28 @@ pub fn cmdBuild(gpa: Allocator, arena: Allocator, args: []const []const u8) !voi
54215426
.http_client = &http_client,
54225427
.thread_pool = &thread_pool,
54235428
.global_cache = global_cache_directory,
5429+
.read_only = false,
54245430
.recursive = true,
54255431
.debug_hash = false,
54265432
.work_around_btrfs_bug = work_around_btrfs_bug,
54275433
};
54285434
defer job_queue.deinit();
54295435

5436+
if (system_pkg_dir_path) |p| {
5437+
job_queue.global_cache = .{
5438+
.path = p,
5439+
.handle = fs.cwd().openDir(p, .{}) catch |err| {
5440+
fatal("unable to open system package directory '{s}': {s}", .{
5441+
p, @errorName(err),
5442+
});
5443+
},
5444+
};
5445+
job_queue.read_only = true;
5446+
cleanup_build_dir = job_queue.global_cache.handle;
5447+
} else {
5448+
try http_client.loadDefaultProxies();
5449+
}
5450+
54305451
try job_queue.all_fetches.ensureUnusedCapacity(gpa, 1);
54315452
try job_queue.table.ensureUnusedCapacity(gpa, 1);
54325453

@@ -7354,6 +7375,7 @@ fn cmdFetch(
73547375
.thread_pool = &thread_pool,
73557376
.global_cache = global_cache_directory,
73567377
.recursive = false,
7378+
.read_only = false,
73577379
.debug_hash = debug_hash,
73587380
.work_around_btrfs_bug = work_around_btrfs_bug,
73597381
};

0 commit comments

Comments
 (0)