Archived
Found and fixed live against a real test container (VMID 100, lxc-nix-cache on pve.sweet.home) after the previous pct-restore-to-pct-create fix still produced a container that booted into garbled console output: 1. pct create's own CLI default for --unprivileged is privileged (unlike the web UI, whose checkbox defaults the other way), but modules/platforms/lxc.nix sets proxmoxLXC.privileged = false, so the image assumes it's running unprivileged. Real mismatch -- now passes --unprivileged 1 explicitly. 2. The actual root cause of the garbled console: modern (v247+) systemd routinely uses nested user namespaces and credential mounts (even plain getty units, via LoadCredential=-style mechanisms), which AppArmor's default LXC confinement denies without --features nesting=1,keyctl=1. Confirmed via the host's kernel audit log: every getty unit was crash-looping on a denied /run/credentials/* mount every ~3s, and core services like nsncd failed userns_create the same way -- the system never finished activating. Fixed live (pct set + restart on the running test container) before committing the script change: systemctl is-system-running went from never completing to "running" with zero failed units. 3. --memory doesn't touch swap -- confirmed live it silently stayed at Proxmox's own 512M default with --memory 2048. Now defaults --swap to whatever --memory resolves to. docs/auto-installer.md's manual pct create walkthrough gets the same fixes, with the "why" for each flag, since a human following it by hand would hit the identical bugs. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01La55Nsss8jZ7ZuzUV9mfot
101 lines
4.8 KiB
Bash
Executable File
101 lines
4.8 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
# Shared config for scripts/*.sh. Source this instead of hardcoding a
|
|
# second copy of these values in every script:
|
|
# source "$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)/env.sh"
|
|
# Every variable can still be overridden per-invocation via the
|
|
# environment (e.g. PROXMOX_STORAGE=tank-nvme ./scripts/create-proxmox-resource.sh ...)
|
|
# since each one only sets a default if unset.
|
|
|
|
# SSH-reachable Proxmox node that scripts/create-proxmox-resource.sh runs
|
|
# pct/qm on. Matches the Proxmox web UI hostname already used in
|
|
# hosts/nixos/home.nix's desktop shortcuts (pve.<homeDomain> from
|
|
# variables.nix) -- change this if that's not actually reachable over SSH,
|
|
# or if you're targeting a different node in a multi-node cluster.
|
|
: "${PROXMOX_HOST:=pve.sweet.home}"
|
|
: "${PROXMOX_SSH_USER:=root}"
|
|
|
|
# Storage pool names -- Proxmox's own stock-install defaults, but this
|
|
# varies a lot by setup (ZFS pool name, custom LVM-thin volume, etc.).
|
|
# Verify with `pvesm status` on the node and correct these if wrong.
|
|
: "${PROXMOX_STORAGE:=local-lvm}" # VM disks / CT rootfs
|
|
: "${PROXMOX_ISO_STORAGE:=local}" # uploaded images/ISOs/CT templates
|
|
|
|
: "${PROXMOX_BRIDGE:=vmbr0}"
|
|
|
|
# Fallback resource sizing when a script doesn't get --cores/--memory.
|
|
: "${PROXMOX_DEFAULT_CORES:=2}"
|
|
: "${PROXMOX_DEFAULT_MEMORY_MB:=2048}"
|
|
|
|
# `pct create` (unlike `pct restore`) requires an explicit rootfs size --
|
|
# no backup metadata to infer it from. Matches Proxmox's own GUI default.
|
|
: "${PROXMOX_DEFAULT_LXC_DISK_GB:=8}"
|
|
|
|
# `pct create --memory` only sets RAM -- swap is a wholly separate
|
|
# parameter that otherwise silently stays at Proxmox's own 512M default
|
|
# regardless of --memory (confirmed: creating with --memory 2048 left
|
|
# swap at 512). create-proxmox-resource.sh defaults --swap to whatever
|
|
# --memory resolves to at runtime rather than a static value here, so it
|
|
# tracks a --memory picked at the CLI too, not just the default above.
|
|
|
|
# Required for a modern (v247+) systemd guest to actually boot as an
|
|
# unprivileged container: systemd's routine use of nested user namespaces
|
|
# and credential mounts (LoadCredential=, DynamicUser=, etc. -- used even
|
|
# by plain getty units) gets denied by AppArmor's default LXC confinement
|
|
# without these. Confirmed live: without them, every getty unit
|
|
# crash-loops on a denied `/run/credentials/*` mount every ~3s (visible
|
|
# as garbage on the console) and core services like nsncd fail the same
|
|
# way on userns_create; system.build.tarball never finishes activating.
|
|
: "${PROXMOX_DEFAULT_LXC_FEATURES:=nesting=1,keyctl=1}"
|
|
|
|
export PROXMOX_HOST PROXMOX_SSH_USER PROXMOX_STORAGE PROXMOX_ISO_STORAGE \
|
|
PROXMOX_BRIDGE PROXMOX_DEFAULT_CORES PROXMOX_DEFAULT_MEMORY_MB \
|
|
PROXMOX_DEFAULT_LXC_DISK_GB PROXMOX_DEFAULT_LXC_FEATURES
|
|
|
|
# Matches variables.nix's nixCacheHost -- update both if it ever changes.
|
|
: "${NIX_CACHE_HOST:=nix-cache}"
|
|
export NIX_CACHE_HOST
|
|
|
|
# nix_extra_opts: call as a plain statement (NOT inside $(...)/<(...) --
|
|
# that forks a subshell, and the whole point is exporting a decision back
|
|
# into *this* shell) to populate the global NIX_OPTS array with whatever
|
|
# extra `nix`/`nix-shell` CLI options are needed to avoid nix-cache when
|
|
# it's unreachable:
|
|
# nix_extra_opts
|
|
# nix build "${NIX_OPTS[@]}" ...
|
|
#
|
|
# Without this, every single `nix eval`/`nix build` call retries each
|
|
# store path against a dead substituter up to 5 times with backoff
|
|
# (confirmed: ~15s+ per lookup even with a short connect-timeout, because
|
|
# nix's own retry count isn't controllable that way), and separately
|
|
# tries it as a remote builder too -- both fail independently, so both
|
|
# are checked.
|
|
#
|
|
# Checked with a single fast `curl`/TCP probe (bypassing nix's retry logic
|
|
# entirely) the first time this is called in a given process, and the
|
|
# result is exported as NIX_EXTRA_OPTS so a script that shells out to
|
|
# another script in this repo (e.g. create-proxmox-resource.sh calling
|
|
# sync-host-keys.sh) reuses the same decision instead of probing twice.
|
|
declare -a NIX_OPTS=()
|
|
|
|
nix_extra_opts() {
|
|
if [[ -n "${NIX_EXTRA_OPTS_DECIDED:-}" ]]; then
|
|
if [[ -n "${NIX_EXTRA_OPTS:-}" ]]; then
|
|
eval "NIX_OPTS=(${NIX_EXTRA_OPTS})"
|
|
else
|
|
NIX_OPTS=()
|
|
fi
|
|
return
|
|
fi
|
|
export NIX_EXTRA_OPTS_DECIDED=1
|
|
NIX_OPTS=()
|
|
if ! curl --silent --fail --max-time 3 "http://${NIX_CACHE_HOST}/nix-cache-info" >/dev/null 2>&1; then
|
|
echo "nix-cache (http://${NIX_CACHE_HOST}) is unreachable -- skipping it (substituter + remote builder) for the rest of this run." >&2
|
|
NIX_OPTS=(--option substituters "https://cache.nixos.org/" --builders "")
|
|
elif ! timeout 3 bash -c "cat < /dev/tcp/${NIX_CACHE_HOST}/22" >/dev/null 2>&1; then
|
|
echo "nix-cache's SSH remote builder (nixremote@${NIX_CACHE_HOST}:22) is unreachable -- disabling remote builds for the rest of this run." >&2
|
|
NIX_OPTS=(--builders "")
|
|
fi
|
|
printf -v NIX_EXTRA_OPTS '%q ' "${NIX_OPTS[@]}"
|
|
export NIX_EXTRA_OPTS
|
|
}
|