From 93497a57025be656ee1fe8f7777f53222e1218e3 Mon Sep 17 00:00:00 2001 From: David Zbarsky Date: Fri, 11 Sep 2026 18:44:45 -0400 Subject: [PATCH] fix: inspect debs with hermetic bsdtar Use tar.bzl's pinned host binary during repository evaluation. Discover the data archive instead of assuming XZ compression, so Zstandard debs work without host tar or zstd. Remove directory exclusions that suppress file discovery with BSD tar, and report inspection/extraction failures. --- MODULE.bazel | 13 +++++++++++-- apt/private/BUILD.bazel | 8 ++++++++ apt/private/deb_archive.bzl | 16 ++++++++++++++++ apt/private/deb_import.bzl | 15 +++++++++++---- 4 files changed, 46 insertions(+), 6 deletions(-) create mode 100644 apt/private/deb_archive.bzl diff --git a/MODULE.bazel b/MODULE.bazel index 5ab4b8cc..9eb7f149 100644 --- a/MODULE.bazel +++ b/MODULE.bazel @@ -12,7 +12,7 @@ bazel_dep(name = "rules_cc", version = "0.2.8") bazel_dep(name = "rules_java", version = "8.8.0") bazel_dep(name = "rules_shell", version = "0.4.1") bazel_dep(name = "gawk", version = "5.3.2.bcr.3") -bazel_dep(name = "tar.bzl", version = "0.6.0") +bazel_dep(name = "tar.bzl", version = "0.10.4") bazel_dep(name = "yq.bzl", version = "0.3.1") yq_toolchains = use_extension("@yq.bzl//yq:extensions.bzl", "yq") @@ -29,7 +29,16 @@ use_repo(bazel_lib_toolchains, "zstd_toolchains") use_repo(bazel_lib_toolchains, "coreutils_toolchains") tar_toolchains = use_extension("@tar.bzl//tar:extensions.bzl", "toolchains") -use_repo(tar_toolchains, "bsd_tar_toolchains") +use_repo( + tar_toolchains, + "bsd_tar_toolchains", + "bsd_tar_toolchains_darwin_amd64", + "bsd_tar_toolchains_darwin_arm64", + "bsd_tar_toolchains_linux_amd64", + "bsd_tar_toolchains_linux_arm64", + "bsd_tar_toolchains_windows_amd64", + "bsd_tar_toolchains_windows_arm64", +) # Dev dependencies bazel_dep(name = "gazelle", version = "0.34.0", dev_dependency = True, repo_name = "bazel_gazelle") diff --git a/apt/private/BUILD.bazel b/apt/private/BUILD.bazel index bea14893..ed5777b4 100644 --- a/apt/private/BUILD.bazel +++ b/apt/private/BUILD.bazel @@ -55,11 +55,19 @@ bzl_library( deps = ["@bazel_lib//lib:strings"], ) +bzl_library( + name = "deb_archive", + srcs = ["deb_archive.bzl"], + visibility = ["//apt:__subpackages__"], + deps = ["@bazel_lib//lib:repo_utils"], +) + bzl_library( name = "deb_import", srcs = ["deb_import.bzl"], visibility = ["//apt:__subpackages__"], deps = [ + ":deb_archive", ":linker_script", ":pkgconfig", ], diff --git a/apt/private/deb_archive.bzl b/apt/private/deb_archive.bzl new file mode 100644 index 00000000..65f967d7 --- /dev/null +++ b/apt/private/deb_archive.bzl @@ -0,0 +1,16 @@ +"""Inspect Debian data archives with tar.bzl's host toolchain binary.""" + +load("@bazel_lib//lib:repo_utils.bzl", "repo_utils") + +# Repository rules run before toolchain resolution. Use the same pinned +# binary tar.bzl makes available for the repository host. +def host_bsdtar(rctx): + platform = repo_utils.platform(rctx) + binary = "tar.exe" if platform.startswith("windows_") else "tar" + return rctx.path(Label("@bsd_tar_toolchains_{}//:{}".format(platform, binary))) + +def data_archive(rctx, directory = "."): + archives = [path for path in rctx.path(directory).readdir() if path.basename.startswith("data.tar")] + if len(archives) != 1: + fail("expected one data archive, found: %s" % archives) + return archives[0] diff --git a/apt/private/deb_import.bzl b/apt/private/deb_import.bzl index d83dca18..7dccd269 100644 --- a/apt/private/deb_import.bzl +++ b/apt/private/deb_import.bzl @@ -1,7 +1,8 @@ "deb_import" -load(":lockfile.bzl", "lockfile") +load(":deb_archive.bzl", "data_archive", "host_bsdtar") load(":linker_script.bzl", "linker_script") +load(":lockfile.bzl", "lockfile") load(":pkgconfig.bzl", "pkgconfig") load(":util.bzl", "util") @@ -183,7 +184,11 @@ def _remap_linkopts(rctx, extract_dir, so_regular_files, self_files, depends_fil return result.linkopts def _discover_contents(rctx, depends_on, depends_file_map, target_name, mergedusr = False): - result = rctx.execute(["tar", "--exclude='./usr/share/**'", "--exclude='./**/'", "-tvf", "data.tar.xz"]) + archive = data_archive(rctx) + tar = host_bsdtar(rctx) + result = rctx.execute([tar, "-tvf", archive]) + if result.return_code: + fail("failed to inspect %s: %s" % (archive, result.stderr)) contents_raw = result.stdout.splitlines() so_files = [] @@ -283,10 +288,12 @@ def _discover_contents(rctx, depends_on, depends_file_map, target_name, mergedus files_to_extract = so_regular_files + pc_files if files_to_extract: rctx.execute(["mkdir", "-p", _EXTRACT_DIR]) - rctx.execute( - ["tar", "-xf", "data.tar.xz", "-C", _EXTRACT_DIR] + + result = rctx.execute( + [tar, "-xf", archive, "-C", _EXTRACT_DIR] + ["./" + f for f in files_to_extract], ) + if result.return_code: + fail("failed to extract %s from %s: %s" % (files_to_extract, archive, result.stderr)) remap_linkopts = _remap_linkopts( rctx,