split out hash because rocky doesnt support it inline
This commit is contained in:
+28
-22
@@ -1,29 +1,32 @@
|
||||
#!/usr/bin/env bash
|
||||
# Configure SPDK nvmf_tgt to serve the diskless root filesystem as a single
|
||||
# READ-ONLY NVMe/TCP namespace (design doc §5, §7).
|
||||
# Configure SPDK nvmf_tgt to serve the diskless root filesystem as TWO READ-ONLY
|
||||
# NVMe/TCP namespaces — erofs DATA and the dm-verity HASH tree (design doc §5, §7).
|
||||
#
|
||||
# rootfs.erofs is the erofs image with the dm-verity hash tree appended in-file;
|
||||
# we expose the WHOLE file as one namespace, and the host splits data/hash with
|
||||
# systemd.verity_root_options=hash-offset= from the kernel cmdline. Integrity is
|
||||
# enforced end-to-end by dm-verity on the host; the target serves it read-only.
|
||||
# Two namespaces (not one with an in-file hash-offset): the target Rocky 9
|
||||
# systemd-veritysetup does not support the hash-offset layout, so the host needs
|
||||
# the verity data and hash on separate block devices. Integrity is enforced
|
||||
# end-to-end by dm-verity on the host; the target serves both read-only.
|
||||
set -euo pipefail
|
||||
|
||||
ROOTFS="/artifacts/rootfs.erofs"
|
||||
ROOTHASH="/artifacts/rootfs.hash"
|
||||
SUBNQN="${SUBNQN:-nqn.2026-06.org.example.fleet:rootfs}"
|
||||
# Fixed, fleet-generic namespace UUID. The host references the root device as
|
||||
# /dev/disk/by-id/nvme-uuid.$ROOT_NS_UUID on the kernel cmdline, which is stable
|
||||
# regardless of NVMe controller enumeration order (the I/O controller can land
|
||||
# on nvme0/nvme1/... depending on whether a transient discovery controller took
|
||||
# a slot first — so a hardcoded /dev/nvme0n1 is unsafe). MUST match
|
||||
# ROOT_NS_UUID in scripts/extract-artifacts.sh, which bakes it into the UKI
|
||||
# cmdline. NOTE: for multi-version serving (TODO #6) make this version-specific
|
||||
# alongside the per-version NQN, so a host can't connect the wrong rootfs.
|
||||
ROOT_NS_UUID="${ROOT_NS_UUID:-f1ee7000-0000-4000-8000-000000000001}"
|
||||
# Fixed, fleet-generic namespace UUIDs. The host references each device as
|
||||
# /dev/disk/by-id/nvme-uuid.<uuid> on the kernel cmdline, stable regardless of
|
||||
# NVMe controller/namespace enumeration order (a transient discovery controller
|
||||
# can shift indices — so a hardcoded /dev/nvmeNnM is unsafe). MUST match
|
||||
# ROOT_DATA_UUID / ROOT_HASH_UUID in scripts/extract-artifacts.sh, which bake
|
||||
# them into the UKI cmdline. NOTE: for multi-version serving (TODO #6) make
|
||||
# these version-specific alongside the per-version NQN, so a host can't connect
|
||||
# the wrong rootfs.
|
||||
ROOT_DATA_UUID="${ROOT_DATA_UUID:-f1ee7000-0000-4000-8000-000000000001}"
|
||||
ROOT_HASH_UUID="${ROOT_HASH_UUID:-f1ee7000-0000-4000-8000-000000000002}"
|
||||
TADDR="${TARGET_ADDR:-0.0.0.0}"
|
||||
TPORT="${TARGET_PORT:-4420}"
|
||||
CPUMASK="${SPDK_CPUMASK:-0x1}"
|
||||
|
||||
[ -s "$ROOTFS" ] || { echo "ERROR: $ROOTFS not found/empty — is ARTIFACT_SRC populated?" >&2; exit 1; }
|
||||
[ -s "$ROOTFS" ] || { echo "ERROR: $ROOTFS not found/empty — is ARTIFACT_SRC populated?" >&2; exit 1; }
|
||||
[ -s "$ROOTHASH" ] || { echo "ERROR: $ROOTHASH not found/empty — rebuild artifacts with the two-namespace layout." >&2; exit 1; }
|
||||
|
||||
# Binary locations differ across SPDK images; fall back to the common path.
|
||||
TGT=$(command -v nvmf_tgt || echo /usr/libexec/spdk/spdk/build/bin/nvmf_tgt)
|
||||
@@ -59,21 +62,24 @@ done
|
||||
echo "==> creating TCP transport"
|
||||
"$RPC" nvmf_create_transport -t TCP -u 16384 -m 8 -c 8192
|
||||
|
||||
echo "==> exposing $ROOTFS as bdev 'rootfs' (4 KiB blocks)"
|
||||
echo "==> exposing $ROOTFS (data) + $ROOTHASH (verity hash) as bdevs (4 KiB blocks)"
|
||||
# -r opens the backing file read-only where supported; harmless if ignored.
|
||||
"$RPC" bdev_aio_create "$ROOTFS" rootfs 4096 -r \
|
||||
|| "$RPC" bdev_aio_create "$ROOTFS" rootfs 4096
|
||||
"$RPC" bdev_aio_create "$ROOTHASH" roothash 4096 -r \
|
||||
|| "$RPC" bdev_aio_create "$ROOTHASH" roothash 4096
|
||||
|
||||
echo "==> creating subsystem $SUBNQN (allow any host — lab/no-auth)"
|
||||
"$RPC" nvmf_create_subsystem "$SUBNQN" -a -s SPDKLAB0000000001 -d FleetRootfs
|
||||
|
||||
echo "==> adding namespace 1 (uuid $ROOT_NS_UUID)"
|
||||
# Read-only is enforced by the bdev_aio '-r' open above (this SPDK's add_ns has
|
||||
# no --read-only flag), plus the :ro image-volume mount and the client's erofs
|
||||
# ro + dm-verity.
|
||||
# -u pins the namespace UUID so the host can reference it as
|
||||
# /dev/disk/by-id/nvme-uuid.$ROOT_NS_UUID (stable across controller indices).
|
||||
"$RPC" nvmf_subsystem_add_ns "$SUBNQN" rootfs -u "$ROOT_NS_UUID"
|
||||
# ro + dm-verity. -u pins each namespace UUID so the host references them as
|
||||
# /dev/disk/by-id/nvme-uuid.<uuid> (stable across controller indices).
|
||||
echo "==> adding namespace 1: data (uuid $ROOT_DATA_UUID)"
|
||||
"$RPC" nvmf_subsystem_add_ns "$SUBNQN" rootfs -u "$ROOT_DATA_UUID"
|
||||
echo "==> adding namespace 2: verity hash (uuid $ROOT_HASH_UUID)"
|
||||
"$RPC" nvmf_subsystem_add_ns "$SUBNQN" roothash -u "$ROOT_HASH_UUID"
|
||||
|
||||
echo "==> adding TCP listener ${TADDR}:${TPORT} to $SUBNQN"
|
||||
"$RPC" nvmf_subsystem_add_listener "$SUBNQN" -t tcp -a "$TADDR" -s "$TPORT"
|
||||
|
||||
Reference in New Issue
Block a user