feat(iso): split the live medium into semantic SquashFS layers
Booting via BMC virtual CD reads the ~2.8 GB filesystem squashfs sequentially during the live-boot toram copy; a mid-read drop of the redirected medium loses the whole copy and fails the boot (v14). Split the rootfs into self-contained semantic layers so a retry re-reads at most one ~500-700 MiB layer, not everything. This is a resilience / reduced-re-read mechanism, not a fix for the virtual-media instability. NVIDIA variants now ship 7 layers (00-base, 05-firmware, 08-desktop, 10-nvidia-driver, 20-nvidia-platform, 30-nvidia-cuda-libs, 40-nvidia-dcgm-cuda) plus an explicit live/filesystem.module that fixes their OverlayFS order; amd/nogpu keep a single squashfs. - lib/squashfs-layers.sh: deterministic classifier (dpkg file ownership plus explicit rules for build.sh-injected files, never a path substring), per-layer mksquashfs, 800 MiB hard ceiling, unsquashfs -s plus strict extraction of every layer, merged-rootfs bootability check. - build.sh: split the monolith after the full lb build, verify and merge, write the module file, delete the monolith only then; abort before ISO assembly on any failure. Runs the builder test suites up front. - fast-path: force a full build for a multi-layer medium; fast_path_repack_squashfs hard-refuses (it would drop layers). - iso-validation.sh: validate_iso_squashfs_layers (module vs layer set match, size ceiling, no lone giant squashfs) and validate_iso_media_integrity (xorriso -check_media). - bee-install: honour filesystem.module order, abort on any layer failure. - 9013-toram-retry: record the real rsync exit code (it printed a false rc=0) and correct the "resumes the tail" comment (rsync without --partial keeps only fully-copied layers). No unsafe partial resume. - tests: test-squashfs-layers.sh plus a multi-layer guard in test-build-libs.sh; both run at the top of every build. - docs: bible-local architecture and decision, iso/README, iso-build-rules. Verified by a full nvidia build: 7 layers 622/199/256/466/37/567/562 MiB, every validator passes, xorriso -check_media good, merged rootfs bootable. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Sonnet 5
parent
bc57b85d3f
commit
b8c45d54c1
@@ -79,8 +79,47 @@ export GOCACHE GOMODCACHE
|
||||
. "${BUILDER_DIR}/lib/iso-validation.sh"
|
||||
. "${BUILDER_DIR}/lib/template.sh"
|
||||
. "${BUILDER_DIR}/lib/bootloader.sh"
|
||||
. "${BUILDER_DIR}/lib/squashfs-layers.sh"
|
||||
. "${BUILDER_DIR}/lib/fast-path.sh"
|
||||
|
||||
# Whether this variant ships a multi-layer live medium (semantic squashfs
|
||||
# layers + live/filesystem.module) instead of one monolithic squashfs.
|
||||
case "${BUILD_VARIANT}" in
|
||||
nvidia|nvidia-legacy) BEE_MULTILAYER_SQUASHFS=1 ;;
|
||||
*) BEE_MULTILAYER_SQUASHFS=0 ;;
|
||||
esac
|
||||
|
||||
# bee_split_squashfs_layers <monolith_squashfs> <live_dir>
|
||||
# Deterministically replace the monolith with the semantic layer set. Runs as a
|
||||
# set -e subshell: any failed sub-step aborts the build (via run_step) before the
|
||||
# outer ISO is assembled, so a partial layer set is never published.
|
||||
bee_split_squashfs_layers() (
|
||||
set -e
|
||||
_mono="$1"
|
||||
_live="$2"
|
||||
[ -f "${_mono}" ] || { echo "ERROR: monolith squashfs not found: ${_mono}" >&2; exit 1; }
|
||||
|
||||
_wd="$(mktemp -d "${CACHE_ROOT}/layer-split-${BUILD_VARIANT}.XXXXXX")"
|
||||
trap 'rm -rf "${_wd}"' EXIT
|
||||
_root="${_wd}/root"
|
||||
_cls="${_wd}/cls"
|
||||
echo "=== splitting $(basename "${_mono}") into semantic layers ==="
|
||||
unsquashfs -d "${_root}" "${_mono}"
|
||||
|
||||
bee_layer_classify "${_root}" "${BUILD_VARIANT}" "${_cls}"
|
||||
bee_layer_build "${_root}" "${_cls}" "${_live}" "${PROJECT_VERSION_EFFECTIVE}" "${BUILD_VARIANT}"
|
||||
bee_layer_verify_each "${_live}" "${PROJECT_VERSION_EFFECTIVE}" "${BUILD_VARIANT}"
|
||||
bee_layer_merge "${_live}" "${PROJECT_VERSION_EFFECTIVE}" "${BUILD_VARIANT}" "${_wd}/merged"
|
||||
bee_layer_write_module_file "${_live}" "${PROJECT_VERSION_EFFECTIVE}" "${BUILD_VARIANT}"
|
||||
|
||||
# Publish the ownership map on the medium for bee-install / debugging, then
|
||||
# drop the monolith - only now that every layer exists and verifies.
|
||||
cp "${_cls}/classify-report.txt" "${_live}/filesystem.layers.txt"
|
||||
rm -f "${_mono}"
|
||||
echo "=== semantic layer split complete ==="
|
||||
ls -la "${_live}"/filesystem-v*.squashfs "${_live}/filesystem.module"
|
||||
)
|
||||
|
||||
resolve_project_version() {
|
||||
if [ -n "${BEE_VERSION:-}" ]; then
|
||||
echo "${BEE_VERSION}"
|
||||
@@ -185,6 +224,10 @@ LOG_OUT="${LOG_DIR}/build.log"
|
||||
|
||||
start_build_log
|
||||
|
||||
# Fail fast on builder-library regressions before the 30-60 min ISO build.
|
||||
run_step "builder library tests" "01-lib-tests" sh "${BUILDER_DIR}/test-build-libs.sh"
|
||||
run_step "squashfs layer tests" "02-squashfs-layer-tests" sh "${BUILDER_DIR}/test-squashfs-layers.sh"
|
||||
|
||||
# Auto-detect kernel ABI: refresh apt index, then query current linux-image-amd64 dependency.
|
||||
# If headers for the detected ABI are not yet installed (kernel updated since image build),
|
||||
# install them on the fly so NVIDIA modules and ISO kernel always match.
|
||||
@@ -649,6 +692,8 @@ if ! needs_full_build; then
|
||||
validate_iso_grub_assets "$ISO_RAW"
|
||||
validate_iso_nvidia_runtime "$ISO_RAW"
|
||||
validate_iso_rootfs_layout "$ISO_RAW"
|
||||
validate_iso_squashfs_layers "$ISO_RAW"
|
||||
validate_iso_media_integrity "$ISO_RAW"
|
||||
cp "$ISO_RAW" "$ISO_OUT"
|
||||
echo ""
|
||||
echo "=== done (${BUILD_VARIANT}, fast-path) ==="
|
||||
@@ -677,6 +722,15 @@ if [ -f "${_std_sq}" ] && [ "${_std_sq}" != "${_ver_sq}" ]; then
|
||||
mv "${_std_sq}" "${_ver_sq}"
|
||||
echo "=== squashfs renamed: filesystem.squashfs -> ${SQUASHFS_FILENAME} ==="
|
||||
fi
|
||||
|
||||
# Split the monolith into semantic layers before checksums / ISO assembly so
|
||||
# md5sum.txt covers the layers and the module file, and the outer ISO carries
|
||||
# them. Single-layer variants (amd, nogpu) keep the monolith untouched.
|
||||
if [ "${BEE_MULTILAYER_SQUASHFS}" = "1" ]; then
|
||||
run_step "split squashfs into semantic layers" "90b-squashfs-layers" \
|
||||
bee_split_squashfs_layers "${_ver_sq}" "${LB_DIR}/binary/live"
|
||||
fi
|
||||
|
||||
reset_live_build_stage "${LB_DIR}" "binary_checksums"
|
||||
reset_live_build_stage "${LB_DIR}" "binary_iso"
|
||||
reset_live_build_stage "${LB_DIR}" "binary_zsync"
|
||||
@@ -711,6 +765,8 @@ if [ -f "$ISO_RAW" ]; then
|
||||
validate_iso_grub_assets "$ISO_RAW"
|
||||
validate_iso_nvidia_runtime "$ISO_RAW"
|
||||
validate_iso_rootfs_layout "$ISO_RAW"
|
||||
validate_iso_squashfs_layers "$ISO_RAW"
|
||||
validate_iso_media_integrity "$ISO_RAW"
|
||||
cp "$ISO_RAW" "$ISO_OUT"
|
||||
hash_heavy_config > "${FULL_BUILD_HASH_FILE}.new"
|
||||
printf '%s\n' "${DEBIAN_KERNEL_ABI}" > "${FULL_BUILD_ABI_FILE}.new"
|
||||
|
||||
Reference in New Issue
Block a user