From 1ad33f53fea4109160ccfceec94efa2013f3b3b3 Mon Sep 17 00:00:00 2001 From: Andrew Kelley Date: Sun, 8 Oct 2023 16:08:08 -0700 Subject: [PATCH] give build.zig modules access to their dependencies' build.zig modules --- src/Package/Fetch.zig | 37 ++++++++++++++++++++++++++++++++----- src/main.zig | 26 +++++++++++++++++++++++++- 2 files changed, 57 insertions(+), 6 deletions(-) diff --git a/src/Package/Fetch.zig b/src/Package/Fetch.zig index 9b4fc13f6f..d241474cb9 100644 --- a/src/Package/Fetch.zig +++ b/src/Package/Fetch.zig @@ -58,6 +58,12 @@ has_build_zig: bool, /// Indicates whether the task aborted due to an out-of-memory condition. oom_flag: bool, +// This field is used by the CLI only, untouched by this file. + +/// The module for this `Fetch` tasks's package, which exposes `build.zig` as +/// the root source file. +module: ?*Package.Module, + /// Contains shared state among all `Fetch` tasks. pub const JobQueue = struct { mutex: std.Thread.Mutex = .{}, @@ -147,10 +153,10 @@ pub const JobQueue = struct { \\ ); for (manifest.dependencies.keys(), manifest.dependencies.values()) |name, dep| { - const h = dep.hash orelse continue; + const h = depDigest(fetch.package_root, jq.global_cache, dep) orelse continue; try buf.writer().print( " .{{ \"{}\", \"{}\" }},\n", - .{ std.zig.fmtEscapes(name), std.zig.fmtEscapes(h) }, + .{ std.zig.fmtEscapes(name), std.zig.fmtEscapes(&h) }, ); } @@ -179,10 +185,10 @@ pub const JobQueue = struct { const root_manifest = &root_fetch.manifest.?; for (root_manifest.dependencies.keys(), root_manifest.dependencies.values()) |name, dep| { - const h = dep.hash orelse continue; + const h = depDigest(root_fetch.package_root, jq.global_cache, dep) orelse continue; try buf.writer().print( " .{{ \"{}\", \"{}\" }},\n", - .{ std.zig.fmtEscapes(name), std.zig.fmtEscapes(h) }, + .{ std.zig.fmtEscapes(name), std.zig.fmtEscapes(&h) }, ); } try buf.appendSlice("};\n"); @@ -258,7 +264,7 @@ pub fn run(f: *Fetch) RunError!void { } f.package_root = pkg_root; try loadManifest(f, pkg_root); - try checkBuildFileExistence(f); + if (!f.has_build_zig) try checkBuildFileExistence(f); if (!f.job_queue.recursive) return; return queueJobsForDeps(f); }, @@ -604,6 +610,8 @@ fn queueJobsForDeps(f: *Fetch) RunError!void { .actual_hash = undefined, .has_build_zig = false, .oom_flag = false, + + .module = null, }; } @@ -1400,6 +1408,25 @@ const Filter = struct { } }; +pub fn depDigest( + pkg_root: Package.Path, + cache_root: Cache.Directory, + dep: Manifest.Dependency, +) ?Manifest.MultiHashHexDigest { + if (dep.hash) |h| return h[0..Manifest.multihash_hex_digest_len].*; + + switch (dep.location) { + .url => return null, + .path => |rel_path| { + var buf: [fs.MAX_PATH_BYTES]u8 = undefined; + var fba = std.heap.FixedBufferAllocator.init(&buf); + const new_root = pkg_root.resolvePosix(fba.allocator(), rel_path) catch + return null; + return relativePathDigest(new_root, cache_root); + }, + } +} + // These are random bytes. const package_hash_prefix_cached = [8]u8{ 0x53, 0x7e, 0xfa, 0x94, 0x65, 0xe9, 0xf8, 0x73 }; const package_hash_prefix_project = [8]u8{ 0xe1, 0x25, 0xee, 0xfa, 0xa6, 0x17, 0x38, 0xcc }; diff --git a/src/main.zig b/src/main.zig index 5dc4b0c9c9..5a57b3c32d 100644 --- a/src/main.zig +++ b/src/main.zig @@ -4870,8 +4870,10 @@ pub fn cmdBuild(gpa: Allocator, arena: Allocator, args: []const []const u8) !voi .manifest = null, .manifest_ast = undefined, .actual_hash = undefined, - .has_build_zig = false, + .has_build_zig = true, .oom_flag = false, + + .module = &build_mod, }; job_queue.all_fetches.appendAssumeCapacity(&fetch); @@ -4922,6 +4924,26 @@ pub fn cmdBuild(gpa: Allocator, arena: Allocator, args: []const []const u8) !voi }); const hash_cloned = try arena.dupe(u8, &hash); deps_mod.deps.putAssumeCapacityNoClobber(hash_cloned, m); + f.module = m; + } + + // Each build.zig module needs access to each of its + // dependencies' build.zig modules by name. + for (fetches) |f| { + const mod = f.module orelse continue; + const man = f.manifest orelse continue; + const dep_names = man.dependencies.keys(); + try mod.deps.ensureUnusedCapacity(arena, @intCast(dep_names.len)); + for (dep_names, man.dependencies.values()) |name, dep| { + const dep_digest = Package.Fetch.depDigest( + f.package_root, + global_cache_directory, + dep, + ) orelse continue; + const dep_mod = job_queue.table.get(dep_digest).?.module orelse continue; + const name_cloned = try arena.dupe(u8, name); + mod.deps.putAssumeCapacityNoClobber(name_cloned, dep_mod); + } } } } @@ -6751,6 +6773,8 @@ fn cmdFetch( .actual_hash = undefined, .has_build_zig = false, .oom_flag = false, + + .module = null, }; defer fetch.deinit();