-
Notifications
You must be signed in to change notification settings - Fork 10
Add Packer configuration to build a minimal Alpine 3.23 UEFI VM for XCP-ng tests #523
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Draft
glehmann
wants to merge
1
commit into
master
Choose a base branch
from
gln/packer-alpine-uefi-xcpng-loun
base: master
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
+261
−0
Draft
Changes from all commits
Commits
File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1 @@ | ||
| export |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,108 @@ | ||
| # Packer: Alpine 3.23 Minimal UEFI for XCP-ng | ||
|
|
||
| Builds a minimal Alpine Linux 3.23.4 VM image (XVA, zstd-compressed) for use | ||
| in xcp-ng-tests. The image is UEFI-booted, has the XCP-ng guest tools | ||
| installed, and allows root SSH access using the xcp-ng CI public keys. | ||
|
|
||
| ## VM Specs | ||
|
|
||
| | Property | Value | | ||
| |-------------|------------------------------| | ||
| | OS | Alpine Linux 3.23.4 (x86_64) | | ||
| | vCPUs | 1 | | ||
| | RAM | 256 MiB | | ||
| | Disk | 512 MiB | | ||
| | Boot | UEFI (grub + GPT) | | ||
| | Network | DHCP (eth0) | | ||
| | Format | XVA (zstd) | | ||
| | Guest tools | xe-guest-utilities (apk) | | ||
|
|
||
| ## Prerequisites | ||
|
|
||
| ### On the machine running Packer | ||
|
|
||
| - [Packer](https://developer.hashicorp.com/packer) (tested with v1.x) | ||
| - The `xenserver-iso` builder plugin from | ||
| [xenserver/packer-plugin-xenserver](https://github.com/xenserver/packer-plugin-xenserver) | ||
| - Python 3 with `libarchive-c==5.3` (for zstd post-processing): | ||
|
|
||
| ```sh | ||
| pip install 'libarchive-c==5.3' | ||
| ``` | ||
|
|
||
| ### On the XCP-ng host | ||
|
|
||
| - An ISO SR where Packer can upload the Alpine ISO (the plugin uploads it | ||
| automatically if you use `iso_url`) | ||
| - A network accessible from the build machine; the default variable value is | ||
| `Pool-wide network associated with eth0` — override with `network_name` if | ||
| needed | ||
|
|
||
| ## Building | ||
|
|
||
| ```sh | ||
| cd packer/ | ||
| packer init alpine-3.23-uefi.pkr.hcl | ||
| packer build \ | ||
| -var xen_host=<XCP-ng IP or hostname> \ | ||
| -var xen_password=<XCP-ng root password> \ | ||
| alpine-3.23-uefi.pkr.hcl | ||
| ``` | ||
|
|
||
| Optional overrides: | ||
|
|
||
| ```sh | ||
| -var xen_username=root # default: root | ||
| -var network_name="<name>" # default: Pool-wide network associated with eth0 | ||
| -var root_password=<password> # temporary build password; default: packer | ||
| ``` | ||
|
|
||
| The output XVA is written to: | ||
|
|
||
| ``` | ||
| output-alpine-3.23-uefi/alpine-3.23-uefi.xva | ||
| ``` | ||
|
|
||
| After the build the post-processor rewrites it in-place with zstd compression | ||
| and sets the bridge to `xenbr0`. | ||
|
|
||
| ## Directory structure | ||
|
|
||
| ``` | ||
| packer/ | ||
| ├── alpine-3.23-uefi.pkr.hcl # Packer build definition (HCL) | ||
| ├── http_files/ | ||
| │ └── answers.txt # Alpine setup-alpine answerfile | ||
| └── scripts/ | ||
| └── cleanup.sh # Post-install cleanup run inside the VM | ||
| ``` | ||
|
|
||
| ## Notes | ||
|
|
||
| - The Alpine guest tools ISO `install.sh` script does not support Alpine; | ||
| `xe-guest-utilities` is installed from the Alpine community repository | ||
| instead. | ||
| - `ROOTSSHKEY` in `answers.txt` injects the xcp-ng CI public keys during | ||
| installation, so no separate provisioner step is needed for SSH keys. | ||
| - `USE_EFI=1` is passed on the kernel cmdline via `boot_command`; this makes | ||
| `setup-disk` use grub and a GPT layout automatically. | ||
| - Swap is disabled (`SWAP_SIZE=0`) to keep the image within 512 MiB. | ||
|
|
||
| ## Troubleshooting | ||
|
|
||
| **Boot hangs / VNC never gets past the boot prompt** | ||
| : Increase `boot_wait` in the JSON (default `10s`) and ensure VNC is | ||
| reachable from the Packer host. | ||
|
|
||
| **SSH timeout** | ||
| : The install takes up to ~3 minutes on a busy host. Increase | ||
| `ssh_wait_timeout` if needed. | ||
|
|
||
| **Disk full during install** | ||
| : If `setup-disk` fails due to space, the disk size can be bumped to 1024 MB | ||
| by passing `-var disk_size=1024` — but note that the builder does not expose | ||
| this directly; you would need to edit the JSON. | ||
|
|
||
| **xva_bridge.py fails** | ||
| : Ensure `libarchive-c==5.3` is installed. Other versions may not work due to | ||
| internal API usage. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,115 @@ | ||
| packer { | ||
| required_plugins { | ||
| xenserver = { | ||
| version = ">= v0.11.0" | ||
| source = "github.com/vatesfr/xenserver" | ||
| } | ||
| } | ||
| } | ||
|
|
||
| variable "xen_host" { | ||
| type = string | ||
| description = "XCP-ng pool master hostname or IP" | ||
| } | ||
|
|
||
| variable "xen_username" { | ||
| type = string | ||
| description = "XCP-ng SSH username" | ||
| default = "root" | ||
| } | ||
|
|
||
| variable "xen_password" { | ||
| type = string | ||
| description = "XCP-ng SSH password" | ||
| sensitive = true | ||
| } | ||
|
|
||
| variable "network_name" { | ||
| type = string | ||
| description = "Name of the XCP-ng network to attach the VM to" | ||
| default = "Pool-wide network associated with eth0" | ||
| } | ||
|
|
||
| variable "sr_name" { | ||
| type = string | ||
| description = "Name of the SR to store the VM disk on (defaults to pool default)" | ||
| default = "" | ||
| } | ||
|
|
||
| variable "sr_iso_name" { | ||
| type = string | ||
| description = "Name of the ISO SR to upload the Alpine ISO to (defaults to pool default)" | ||
| default = "" | ||
| } | ||
|
|
||
| variable "root_password" { | ||
| type = string | ||
| description = "Temporary root password set during the build" | ||
| default = "vateslab" | ||
| sensitive = true | ||
| } | ||
|
|
||
| source "xenserver-iso" "alpine" { | ||
| remote_host = var.xen_host | ||
| remote_username = var.xen_username | ||
| remote_password = var.xen_password | ||
|
|
||
| vm_name = "alpine-3.23-uefi" | ||
| vm_description = "Alpine Linux 3.23.4 minimal UEFI - built with Packer" | ||
| vcpus_max = 1 | ||
| vcpus_atstartup = 1 | ||
| vm_memory = 256 | ||
| disk_size = 512 | ||
|
|
||
| firmware = "uefi" | ||
| clone_template = "Other install media" | ||
|
|
||
| network_names = [var.network_name] | ||
|
|
||
| sr_name = var.sr_name | ||
| sr_iso_name = var.sr_iso_name | ||
|
|
||
| iso_url = "https://dl-cdn.alpinelinux.org/alpine/v3.23/releases/x86_64/alpine-standard-3.23.4-x86_64.iso" | ||
| iso_checksum = "sha256:cfef39c7954f7c4447bcb321b9f4a1cef834536a321309d2c31275d9f2475a4e" | ||
|
|
||
| http_directory = "http_files" | ||
| boot_wait = "30s" | ||
| boot_command = [ | ||
| "root<enter>", | ||
| "<wait3>", | ||
| "ifconfig eth0 up && udhcpc -i eth0<enter><wait5>", | ||
| # "USE<leftShiftOn>-<leftShiftOff>EFI=1 SWAP<leftShiftOn>-<leftShiftOff>SIZE=0 ERASE<leftShiftOn>-<leftShiftOff>DISKS=/dev/xvda setup-alpine -f http://{{.HTTPIP}}:{{.HTTPPort}}/answers.txt<enter>", | ||
| "USE<leftShiftOn>-<leftShiftOff>EFI=1 SWAP<leftShiftOn>-<leftShiftOff>SIZE=0 ERASE<leftShiftOn>-<leftShiftOff>DISKS=/dev/xvda setup-alpine -f https://raw.githubusercontent.com/xcp-ng/xcp-ng-tests/refs/heads/gln/packer-alpine-uefi-xcpng-loun/packer/http_files/answers.txt<enter>", | ||
| "<wait10>", | ||
| "${var.root_password}<enter>", | ||
| "<wait>", | ||
| "${var.root_password}<enter>", | ||
| "<wait60>", | ||
| "apk add --no-cache xe-guest-utilities<enter>", | ||
| "rc-update add xe-guest-utilities default<enter>", | ||
| # "rc-service xe-guest-utilities start<enter>", | ||
| # Remove log files | ||
| "find /var/log -type f -exec truncate -s 0 {} \\;<enter>", | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Those commands look similar to what I can see in Btw, I don't see any occurrence of calling the cleanup script. Is there an implicit mechanism of Packer? |
||
| # Remove temporary files | ||
| "rm -rf /tmp/* /var/tmp/*<enter>", | ||
| # Clear machine-id so each clone gets a unique one | ||
| "echo > /etc/machine-id<enter>", | ||
| # Remove history | ||
| "rm -f /root/.ash_history<enter>", | ||
| "<wait3>", | ||
| ] | ||
|
|
||
| communicator = "none" | ||
| ssh_username = "root" | ||
| ssh_password = var.root_password | ||
| ssh_wait_timeout = "10m" | ||
|
|
||
| install_timeout = "30m" | ||
| output_directory = "export" | ||
| keep_vm = "never" | ||
| format = "xva_zstd" | ||
| } | ||
|
|
||
| build { | ||
| sources = ["xenserver-iso.alpine"] | ||
| } | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,20 @@ | ||
| KEYMAPOPTS=none | ||
| HOSTNAMEOPTS=alpine | ||
| DEVDOPTS=mdev | ||
| INTERFACESOPTS="auto lo | ||
| iface lo inet loopback | ||
| auto eth0 | ||
| iface eth0 inet dhcp | ||
| hostname alpine | ||
| " | ||
| TIMEZONEOPTS=UTC | ||
| PROXYOPTS=none | ||
| APKREPOSOPTS="-1 -c" | ||
| USEROPTS=none | ||
| SSHDOPTS=openssh | ||
| ROOTSSHKEY="ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIMnN/wVdQqHA8KsndfrLS7fktH/IEgxoa533efuXR6rw XCP-ng CI | ||
| ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDKz9uQOoxq6Q0SQ0XTzQHhDolvuo/7EyrDZsYQbRELhcPJG8MT/o5u3HyJFhIP2+HqBSXXgmqRPJUkwz9wUwb2sUwf44qZm/pyPUWOoxyVtrDXzokU/uiaNKUMhbnfaXMz6Ogovtjua63qld2+ZRXnIgrVtYKtYBeu/qKGVSnf4FTOUKl1w3uKkr59IUwwAO8ay3wVnxXIHI/iJgq6JBgQNHbn3C/SpYU++nqL9G7dMyqGD36QPFuqH/cayL8TjNZ67TgAzsPX8OvmRSqjrv3KFbeSlpS/R4enHkSemhgfc8Z2f49tE7qxWZ6x4Uyp5E6ur37FsRf/tEtKIUJGMRXN XCP-ng CI" | ||
| NTPOPTS=none | ||
| DISKOPTS="-m sys /dev/xvda" | ||
| LBUOPTS=none | ||
| APKCACHEOPTS=none |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,17 @@ | ||
| #!/bin/sh | ||
| set -e | ||
|
|
||
| # Remove apk cache | ||
| rm -rf /var/cache/apk/* | ||
|
|
||
| # Remove log files | ||
| find /var/log -type f -exec truncate -s 0 {} \; | ||
|
|
||
| # Remove temporary files | ||
| rm -rf /tmp/* /var/tmp/* | ||
|
|
||
| # Clear machine-id so each clone gets a unique one | ||
| printf '' > /etc/machine-id 2>/dev/null || true | ||
|
|
||
| # Remove history | ||
| rm -f /root/.ash_history /root/.bash_history |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The value of
-fflag should be generic, isn't it?What do you think of using an hcl variable to enable configuration here?