| ... | @@ -447,7 +447,7 @@ fn runResource( | ... | @@ -447,7 +447,7 @@ fn runResource( |
| 447 | const rand_int = std.crypto.random.int(u64); | 447 | const rand_int = std.crypto.random.int(u64); |
| 448 | const tmp_dir_sub_path = "tmp" ++ s ++ Manifest.hex64(rand_int); | 448 | const tmp_dir_sub_path = "tmp" ++ s ++ Manifest.hex64(rand_int); |
| 449 | | 449 | |
| 450 | const package_sub_path = blk: { | 450 | const package_sub_path, const size = blk: { |
| 451 | const tmp_directory_path = try cache_root.join(arena, &.{tmp_dir_sub_path}); | 451 | const tmp_directory_path = try cache_root.join(arena, &.{tmp_dir_sub_path}); |
| 452 | var tmp_directory: Cache.Directory = .{ | 452 | var tmp_directory: Cache.Directory = .{ |
| 453 | .path = tmp_directory_path, | 453 | .path = tmp_directory_path, |
| ... | @@ -499,12 +499,14 @@ fn runResource( | ... | @@ -499,12 +499,14 @@ fn runResource( |
| 499 | // Empty directories have already been omitted by `unpackResource`. | 499 | // Empty directories have already been omitted by `unpackResource`. |
| 500 | // Compute the package hash based on the remaining files in the temporary | 500 | // Compute the package hash based on the remaining files in the temporary |
| 501 | // directory. | 501 | // directory. |
| 502 | f.actual_hash = try computeHash(f, pkg_path, filter); | 502 | f.actual_hash, const size = try computeHash(f, pkg_path, filter); |
| 503 | | 503 | |
| 504 | break :blk if (unpack_result.root_dir.len > 0) | 504 | const pkg_sub_path = if (unpack_result.root_dir.len > 0) |
| 505 | try fs.path.join(arena, &.{ tmp_dir_sub_path, unpack_result.root_dir }) | 505 | try fs.path.join(arena, &.{ tmp_dir_sub_path, unpack_result.root_dir }) |
| 506 | else | 506 | else |
| 507 | tmp_dir_sub_path; | 507 | tmp_dir_sub_path; |
| | 508 | |
| | 509 | break :blk .{ pkg_sub_path, size }; |
| 508 | }; | 510 | }; |
| 509 | | 511 | |
| 510 | // Rename the temporary directory into the global zig package cache | 512 | // Rename the temporary directory into the global zig package cache |
| ... | @@ -513,6 +515,14 @@ fn runResource( | ... | @@ -513,6 +515,14 @@ fn runResource( |
| 513 | // by the system. This is done even if the hash is invalid, in case the | 515 | // by the system. This is done even if the hash is invalid, in case the |
| 514 | // package with the different hash is used in the future. | 516 | // package with the different hash is used in the future. |
| 515 | | 517 | |
| | 518 | const name = f.manifest.?.name; |
| | 519 | const semver = f.manifest.?.version; |
| | 520 | const new_hash = Package.Manifest.NewHashDecoded.init(name, semver, @intCast(size), f.actual_hash); |
| | 521 | const encoded = new_hash.encode(); |
| | 522 | std.debug.print("new hash: {s}\n", .{encoded.toSlice()}); |
| | 523 | |
| | 524 | if (true) std.process.exit(0); |
| | 525 | |
| 516 | f.package_root = .{ | 526 | f.package_root = .{ |
| 517 | .root_dir = cache_root, | 527 | .root_dir = cache_root, |
| 518 | .sub_path = try arena.dupe(u8, "p" ++ s ++ Manifest.hexDigest(f.actual_hash)), | 528 | .sub_path = try arena.dupe(u8, "p" ++ s ++ Manifest.hexDigest(f.actual_hash)), |
| ... | @@ -1420,7 +1430,7 @@ fn computeHash( | ... | @@ -1420,7 +1430,7 @@ fn computeHash( |
| 1420 | f: *Fetch, | 1430 | f: *Fetch, |
| 1421 | pkg_path: Cache.Path, | 1431 | pkg_path: Cache.Path, |
| 1422 | filter: Filter, | 1432 | filter: Filter, |
| 1423 | ) RunError!Manifest.Digest { | 1433 | ) RunError!struct { Manifest.Digest, u64 } { |
| 1424 | // All the path name strings need to be in memory for sorting. | 1434 | // All the path name strings need to be in memory for sorting. |
| 1425 | const arena = f.arena.allocator(); | 1435 | const arena = f.arena.allocator(); |
| 1426 | const gpa = f.arena.child_allocator; | 1436 | const gpa = f.arena.child_allocator; |
| ... | @@ -1499,6 +1509,7 @@ fn computeHash( | ... | @@ -1499,6 +1509,7 @@ fn computeHash( |
| 1499 | .normalized_path = try normalizePathAlloc(arena, entry_pkg_path), | 1509 | .normalized_path = try normalizePathAlloc(arena, entry_pkg_path), |
| 1500 | .kind = kind, | 1510 | .kind = kind, |
| 1501 | .hash = undefined, // to be populated by the worker | 1511 | .hash = undefined, // to be populated by the worker |
| | 1512 | .size = undefined, // to be populated by the worker |
| 1502 | .failure = undefined, // to be populated by the worker | 1513 | .failure = undefined, // to be populated by the worker |
| 1503 | }; | 1514 | }; |
| 1504 | thread_pool.spawnWg(&wait_group, workerHashFile, .{ root_dir, hashed_file }); | 1515 | thread_pool.spawnWg(&wait_group, workerHashFile, .{ root_dir, hashed_file }); |
| ... | @@ -1540,6 +1551,7 @@ fn computeHash( | ... | @@ -1540,6 +1551,7 @@ fn computeHash( |
| 1540 | | 1551 | |
| 1541 | var hasher = Manifest.Hash.init(.{}); | 1552 | var hasher = Manifest.Hash.init(.{}); |
| 1542 | var any_failures = false; | 1553 | var any_failures = false; |
| | 1554 | var total_size: u64 = 0; |
| 1543 | for (all_files.items) |hashed_file| { | 1555 | for (all_files.items) |hashed_file| { |
| 1544 | hashed_file.failure catch |err| { | 1556 | hashed_file.failure catch |err| { |
| 1545 | any_failures = true; | 1557 | any_failures = true; |
| ... | @@ -1550,6 +1562,7 @@ fn computeHash( | ... | @@ -1550,6 +1562,7 @@ fn computeHash( |
| 1550 | }); | 1562 | }); |
| 1551 | }; | 1563 | }; |
| 1552 | hasher.update(&hashed_file.hash); | 1564 | hasher.update(&hashed_file.hash); |
| | 1565 | total_size += hashed_file.size; |
| 1553 | } | 1566 | } |
| 1554 | for (deleted_files.items) |deleted_file| { | 1567 | for (deleted_files.items) |deleted_file| { |
| 1555 | deleted_file.failure catch |err| { | 1568 | deleted_file.failure catch |err| { |
| ... | @@ -1574,7 +1587,7 @@ fn computeHash( | ... | @@ -1574,7 +1587,7 @@ fn computeHash( |
| 1574 | }; | 1587 | }; |
| 1575 | } | 1588 | } |
| 1576 | | 1589 | |
| 1577 | return hasher.finalResult(); | 1590 | return .{ hasher.finalResult(), total_size }; |
| 1578 | } | 1591 | } |
| 1579 | | 1592 | |
| 1580 | fn dumpHashInfo(all_files: []const *const HashedFile) !void { | 1593 | fn dumpHashInfo(all_files: []const *const HashedFile) !void { |
| ... | @@ -1604,20 +1617,20 @@ fn workerDeleteFile(dir: fs.Dir, deleted_file: *DeletedFile) void { | ... | @@ -1604,20 +1617,20 @@ fn workerDeleteFile(dir: fs.Dir, deleted_file: *DeletedFile) void { |
| 1604 | fn hashFileFallible(dir: fs.Dir, hashed_file: *HashedFile) HashedFile.Error!void { | 1617 | fn hashFileFallible(dir: fs.Dir, hashed_file: *HashedFile) HashedFile.Error!void { |
| 1605 | var buf: [8000]u8 = undefined; | 1618 | var buf: [8000]u8 = undefined; |
| 1606 | var hasher = Manifest.Hash.init(.{}); | 1619 | var hasher = Manifest.Hash.init(.{}); |
| | 1620 | var size: u64 = 0; |
| 1607 | hasher.update(hashed_file.normalized_path); | 1621 | hasher.update(hashed_file.normalized_path); |
| 1608 | | 1622 | |
| 1609 | switch (hashed_file.kind) { | 1623 | switch (hashed_file.kind) { |
| 1610 | .file => { | 1624 | .file => { |
| 1611 | var file = try dir.openFile(hashed_file.fs_path, .{}); | 1625 | var file = try dir.openFile(hashed_file.fs_path, .{}); |
| 1612 | defer file.close(); | 1626 | defer file.close(); |
| 1613 | // Hard-coded false executable bit: https://github.com/ziglang/zig/issues/17463 | | |
| 1614 | hasher.update(&.{ 0, 0 }); | | |
| 1615 | var file_header: FileHeader = .{}; | 1627 | var file_header: FileHeader = .{}; |
| 1616 | while (true) { | 1628 | while (true) { |
| 1617 | const bytes_read = try file.read(&buf); | 1629 | const bytes_read = try file.read(&buf); |
| 1618 | if (bytes_read == 0) break; | 1630 | if (bytes_read == 0) break; |
| 1619 | hasher.update(buf[0..bytes_read]); | 1631 | hasher.update(buf[0..bytes_read]); |
| 1620 | file_header.update(buf[0..bytes_read]); | 1632 | file_header.update(buf[0..bytes_read]); |
| | 1633 | size += bytes_read; |
| 1621 | } | 1634 | } |
| 1622 | if (file_header.isExecutable()) { | 1635 | if (file_header.isExecutable()) { |
| 1623 | try setExecutable(file); | 1636 | try setExecutable(file); |
| ... | @@ -1635,6 +1648,7 @@ fn hashFileFallible(dir: fs.Dir, hashed_file: *HashedFile) HashedFile.Error!void | ... | @@ -1635,6 +1648,7 @@ fn hashFileFallible(dir: fs.Dir, hashed_file: *HashedFile) HashedFile.Error!void |
| 1635 | }, | 1648 | }, |
| 1636 | } | 1649 | } |
| 1637 | hasher.final(&hashed_file.hash); | 1650 | hasher.final(&hashed_file.hash); |
| | 1651 | hashed_file.size = size; |
| 1638 | } | 1652 | } |
| 1639 | | 1653 | |
| 1640 | fn deleteFileFallible(dir: fs.Dir, deleted_file: *DeletedFile) DeletedFile.Error!void { | 1654 | fn deleteFileFallible(dir: fs.Dir, deleted_file: *DeletedFile) DeletedFile.Error!void { |
| ... | @@ -1662,6 +1676,7 @@ const HashedFile = struct { | ... | @@ -1662,6 +1676,7 @@ const HashedFile = struct { |
| 1662 | fs_path: []const u8, | 1676 | fs_path: []const u8, |
| 1663 | normalized_path: []const u8, | 1677 | normalized_path: []const u8, |
| 1664 | hash: Manifest.Digest, | 1678 | hash: Manifest.Digest, |
| | 1679 | size: u64, |
| 1665 | failure: Error!void, | 1680 | failure: Error!void, |
| 1666 | kind: Kind, | 1681 | kind: Kind, |
| 1667 | | 1682 | |