Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 20 additions & 4 deletions internal/vm/qemu.go
Original file line number Diff line number Diff line change
Expand Up @@ -675,16 +675,32 @@ func normalizeArch(arch string) string {
}
}

// needsCIDATASeed reports whether a profile's distro needs the cloud-init seed
// delivered as a CIDATA-labelled disk/ISO rather than the NoCloud-over-SMBIOS
// network seed (the Ubuntu/Debian default). EL (RHEL/AlmaLinux/Rocky/CentOS/
// Oracle), Amazon Linux, and SUSE cloud-init configs do not reliably honour the
// SMBIOS-net seed: on EL8 cloud-init falls back to DataSourceNone and never
// authorises the injected SSH key (observed booting AlmaLinux/Rocky 8). Those
// images do read a CIDATA disk/ConfigDrive, so use that instead.
func needsCIDATASeed(profile Profile) bool {
switch strings.ToLower(strings.TrimSpace(profile.Distro)) {
case "rhel", "almalinux", "rocky", "centos", "centos-stream",
"oracle", "oracle-linux", "amazon-linux", "amazonlinux",
"sles", "suse", "opensuse":
return true
}
// Keep the explicit ID for any profile that omits a recognised distro.
return strings.EqualFold(strings.TrimSpace(profile.ID), "rhel-8-4.18")
}

func seedDeliveryForProfile(profile Profile) seedDeliveryMode {
switch strings.ToLower(strings.TrimSpace(profile.ID)) {
case "rhel-8-4.18":
if needsCIDATASeed(profile) {
if commandAvailable("cloud-localds") {
return seedDeliveryNoCloudConfigDrive
}
return seedDeliveryNoCloudConfigFS
default:
return seedDeliveryNoCloudNet
}
return seedDeliveryNoCloudNet
}

func commandAvailable(name string) bool {
Expand Down
13 changes: 12 additions & 1 deletion internal/vm/qemu_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -378,9 +378,20 @@ func TestSeedDeliveryForProfile(t *testing.T) {
if got := seedDeliveryForProfile(Profile{ID: "rhel-8-4.18"}); got != seedDeliveryNoCloudConfigDrive && got != seedDeliveryNoCloudConfigFS {
t.Fatalf("expected rhel-8-4.18 seed delivery %q or %q, got %q", seedDeliveryNoCloudConfigDrive, seedDeliveryNoCloudConfigFS, got)
}
if got := seedDeliveryForProfile(Profile{ID: "ubuntu-22.04-5.15"}); got != seedDeliveryNoCloudNet {
if got := seedDeliveryForProfile(Profile{ID: "ubuntu-22.04-5.15", Distro: "ubuntu"}); got != seedDeliveryNoCloudNet {
t.Fatalf("expected default seed delivery %q, got %q", seedDeliveryNoCloudNet, got)
}
if got := seedDeliveryForProfile(Profile{ID: "debian-12-6.1", Distro: "debian"}); got != seedDeliveryNoCloudNet {
t.Fatalf("expected debian seed delivery %q, got %q", seedDeliveryNoCloudNet, got)
}
// EL-family / Amazon / SUSE must use the CIDATA disk seed (SMBIOS-net is
// ignored by their cloud-init).
for _, distro := range []string{"almalinux", "rocky", "rhel", "centos-stream", "oracle", "amazon-linux", "sles", "opensuse"} {
got := seedDeliveryForProfile(Profile{ID: distro + "-x", Distro: distro})
if got != seedDeliveryNoCloudConfigDrive && got != seedDeliveryNoCloudConfigFS {
t.Fatalf("expected CIDATA seed for distro %q, got %q", distro, got)
}
}
}

func TestMapFixupArgs(t *testing.T) {
Expand Down
7 changes: 6 additions & 1 deletion scripts/hetzner-bootstrap-vm.sh
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,12 @@ sudo apt-get update -y
sudo apt-get install -y \
build-essential ca-certificates curl git jq make pkg-config \
clang llvm libbpf-dev libelf-dev zlib1g-dev zstd \
qemu-system-x86 qemu-utils qemu-kvm openssh-client
qemu-system-x86 qemu-utils qemu-kvm openssh-client \
cloud-image-utils
# cloud-image-utils provides cloud-localds, used to build a CIDATA ConfigDrive
# ISO seed for EL/Amazon/SUSE guests whose cloud-init ignores the SMBIOS-net
# seed (see internal/vm seedDeliveryForProfile). Without it those guests fall
# back to an unreliable vvfat seed and fail to boot.

# bpfcompat requires Go ${GO_VERSION}; Ubuntu's apt golang is too old, so install
# the official toolchain to /usr/local/go and symlink it onto the default PATH
Expand Down
Loading