Commit b8b3d16256ed

Vincent Demeester <vincent@sbr.pm>
2026-06-29 16:19:14
fix(alpine): DHCP, SSH user, flash and deploy
Switched athena to DHCP (router assigns IP by MAC). Unlocked vincent account and fixed .ssh ownership so SSH pubkey login works. Flash script now stops udiskie service and uses sfdisk instead of parted. Deploy script mounts /boot before rsync on diskless hosts.
1 parent e8e953d
Changed files (4)
alpine
common
hosts
athena
root
etc
network
alpine/common/setup.sh
@@ -39,6 +39,10 @@ rc-update add wg-quick.wg0 default
 # --- Users ---
 adduser -D -s /bin/ash -h /home/vincent vincent
 adduser vincent wheel
+# Unlock account (adduser -D leaves it locked, which blocks SSH pubkey login)
+passwd -u vincent
+# Fix ownership of .ssh (copied from skeleton before user was created)
+chown -R vincent:vincent /home/vincent
 
 # --- Root password disabled, SSH only ---
 # Set a known password for console access (SSH is key-only)
alpine/hosts/athena/root/etc/network/interfaces
@@ -2,7 +2,4 @@ auto lo
 iface lo inet loopback
 
 auto eth0
-iface eth0 inet static
-    address 192.168.1.183
-    netmask 255.255.255.0
-    gateway 192.168.1.1
+iface eth0 inet dhcp
alpine/deploy.sh
@@ -21,6 +21,9 @@ case "$ACTION" in
         echo
         [[ $REPLY =~ ^[Yy]$ ]] || exit 0
 
+        # Mount boot partition (diskless Alpine doesn't mount it by default)
+        ssh "root@${HOST}.vpn" "mkdir -p /boot && mount /dev/mmcblk0p1 /boot 2>/dev/null || true"
+
         # Backup current files (A/B rollback)
         ssh "root@${HOST}.vpn" "cp /boot/initramfs /boot/initramfs.prev 2>/dev/null || true"
         ssh "root@${HOST}.vpn" "cp /boot/vmlinuz-rpi /boot/vmlinuz-rpi.prev 2>/dev/null || true"
@@ -29,6 +32,9 @@ case "$ACTION" in
         rsync -Pv "$IMAGE_DIR/initramfs" "root@${HOST}.vpn:/boot/initramfs"
         rsync -Pv "$IMAGE_DIR/vmlinuz-rpi" "root@${HOST}.vpn:/boot/vmlinuz-rpi" 2>/dev/null || true
 
+        # Unmount boot partition
+        ssh "root@${HOST}.vpn" "umount /boot"
+
         echo "==> Deployed. Reboot $HOST to activate:"
         echo "    ssh root@${HOST}.vpn reboot"
         echo ""
alpine/flash.sh
@@ -40,13 +40,14 @@ read -rp "Are you sure? Type 'yes' to continue: " CONFIRM
 
 echo ""
 echo "==> Unmounting existing partitions on $DEVICE..."
-umount "${DEVICE}"* 2>/dev/null || true
+sudo umount "${DEVICE}"* 2>/dev/null || true
 
 echo "==> Partitioning $DEVICE..."
-parted -s "$DEVICE" mklabel msdos
-parted -s "$DEVICE" mkpart primary fat32 1MiB 257MiB
-parted -s "$DEVICE" mkpart primary ext4 257MiB 769MiB
-parted -s "$DEVICE" set 1 boot on
+sudo sfdisk "$DEVICE" <<EOF
+label: dos
+size=256M, type=c, bootable
+size=512M, type=83
+EOF
 
 # Detect partition naming (sda1 vs mmcblk0p1)
 if [[ "$DEVICE" == *"mmcblk"* ]] || [[ "$DEVICE" == *"nvme"* ]]; then
@@ -57,33 +58,48 @@ else
     PART2="${DEVICE}2"
 fi
 
+# Stop udiskie to prevent auto-mounting during flash
+UDISKIE_WAS_RUNNING=0
+if systemctl --user is-active --quiet udiskie 2>/dev/null; then
+    systemctl --user stop udiskie
+    UDISKIE_WAS_RUNNING=1
+    echo "    (stopped udiskie service to prevent auto-mount)"
+    sleep 1
+elif pkill -x udiskie 2>/dev/null; then
+    UDISKIE_WAS_RUNNING=1
+    echo "    (stopped udiskie to prevent auto-mount)"
+    sleep 1
+fi
+
+sudo umount "${DEVICE}"* 2>/dev/null || true
+
 echo "==> Formatting partitions..."
-mkfs.vfat -n ALPINE "$PART1"
-mkfs.ext4 -L persist -q "$PART2"
+sudo mkfs.vfat -n ALPINE "$PART1"
+sudo mkfs.ext4 -L persist -q "$PART2"
 
 # Mount partitions
 BOOT_MNT=$(mktemp -d)
 PERSIST_MNT=$(mktemp -d)
-trap 'umount "$BOOT_MNT" 2>/dev/null; umount "$PERSIST_MNT" 2>/dev/null; rmdir "$BOOT_MNT" "$PERSIST_MNT" 2>/dev/null' EXIT
+trap 'sudo umount "$BOOT_MNT" 2>/dev/null; sudo umount "$PERSIST_MNT" 2>/dev/null; rmdir "$BOOT_MNT" "$PERSIST_MNT" 2>/dev/null; [ "$UDISKIE_WAS_RUNNING" -eq 1 ] && systemctl --user start udiskie 2>/dev/null || true' EXIT
 
 echo "==> Mounting partitions..."
-mount "$PART1" "$BOOT_MNT"
-mount "$PART2" "$PERSIST_MNT"
+sudo mount "$PART1" "$BOOT_MNT"
+sudo mount "$PART2" "$PERSIST_MNT"
 
 echo "==> Copying boot files..."
-cp -v "$BOOT_DIR"/*.bin "$BOOT_MNT/" 2>/dev/null || true
-cp -v "$BOOT_DIR"/*.elf "$BOOT_MNT/" 2>/dev/null || true
-cp -v "$BOOT_DIR"/*.dat "$BOOT_MNT/" 2>/dev/null || true
-cp -v "$BOOT_DIR"/*.dtb "$BOOT_MNT/" 2>/dev/null || true
-cp -v "$BOOT_DIR"/vmlinuz-rpi "$BOOT_MNT/" 2>/dev/null || true
-cp -v "$BOOT_DIR"/initramfs "$BOOT_MNT/"
-cp -v "$BOOT_DIR"/config.txt "$BOOT_MNT/"
-[ -d "$BOOT_DIR/overlays" ] && cp -rv "$BOOT_DIR/overlays" "$BOOT_MNT/"
-[ -d "$BOOT_DIR/extlinux" ] && cp -rv "$BOOT_DIR/extlinux" "$BOOT_MNT/"
+sudo cp -v "$BOOT_DIR"/*.bin "$BOOT_MNT/" 2>/dev/null || true
+sudo cp -v "$BOOT_DIR"/*.elf "$BOOT_MNT/" 2>/dev/null || true
+sudo cp -v "$BOOT_DIR"/*.dat "$BOOT_MNT/" 2>/dev/null || true
+sudo cp -v "$BOOT_DIR"/*.dtb "$BOOT_MNT/" 2>/dev/null || true
+sudo cp -v "$BOOT_DIR"/vmlinuz-rpi "$BOOT_MNT/" 2>/dev/null || true
+sudo cp -v "$BOOT_DIR"/initramfs "$BOOT_MNT/"
+sudo cp -v "$BOOT_DIR"/config.txt "$BOOT_MNT/"
+[ -d "$BOOT_DIR/overlays" ] && sudo cp -rv "$BOOT_DIR/overlays" "$BOOT_MNT/"
+[ -d "$BOOT_DIR/extlinux" ] && sudo cp -rv "$BOOT_DIR/extlinux" "$BOOT_MNT/"
 
 echo "==> Preparing persist partition..."
-mkdir -p "$PERSIST_MNT/ssh"
-mkdir -p "$PERSIST_MNT/wireguard"
+sudo mkdir -p "$PERSIST_MNT/ssh"
+sudo mkdir -p "$PERSIST_MNT/wireguard"
 
 # Try to copy secrets from the running host
 echo ""
@@ -94,9 +110,9 @@ if ssh -o ConnectTimeout=5 "root@${HOST}.vpn" true 2>/dev/null; then
     echo "    Connected to ${HOST}.vpn"
 
     # SSH host key
-    if ssh "root@${HOST}.vpn" "cat /etc/ssh/ssh_host_ed25519_key" > "$PERSIST_MNT/ssh/ssh_host_ed25519_key" 2>/dev/null; then
-        ssh "root@${HOST}.vpn" "cat /etc/ssh/ssh_host_ed25519_key.pub" > "$PERSIST_MNT/ssh/ssh_host_ed25519_key.pub" 2>/dev/null
-        chmod 600 "$PERSIST_MNT/ssh/ssh_host_ed25519_key"
+    if ssh "root@${HOST}.vpn" "cat /etc/ssh/ssh_host_ed25519_key" | sudo tee "$PERSIST_MNT/ssh/ssh_host_ed25519_key" >/dev/null 2>/dev/null; then
+        ssh "root@${HOST}.vpn" "cat /etc/ssh/ssh_host_ed25519_key.pub" | sudo tee "$PERSIST_MNT/ssh/ssh_host_ed25519_key.pub" >/dev/null 2>/dev/null
+        sudo chmod 600 "$PERSIST_MNT/ssh/ssh_host_ed25519_key"
         echo "    ✓ SSH host key copied"
         FETCHED_SECRETS=1
     else
@@ -104,8 +120,8 @@ if ssh -o ConnectTimeout=5 "root@${HOST}.vpn" true 2>/dev/null; then
     fi
 
     # WireGuard private key
-    if ssh "root@${HOST}.vpn" "cat /etc/wireguard/private.key" > "$PERSIST_MNT/wireguard/private.key" 2>/dev/null; then
-        chmod 600 "$PERSIST_MNT/wireguard/private.key"
+    if ssh "root@${HOST}.vpn" "cat /etc/wireguard/private.key" | sudo tee "$PERSIST_MNT/wireguard/private.key" >/dev/null 2>/dev/null; then
+        sudo chmod 600 "$PERSIST_MNT/wireguard/private.key"
         echo "    ✓ WireGuard private key copied"
         FETCHED_SECRETS=1
     else