在家里尝试了下跑通PXE装机流程,纯流水帐记录,能跑就行。
先说句题外话,我家里是用PVE起的虚拟机,需要注意的是创建VM时网卡型号不能选VirtIO,可能跑DHCP会有问题,选Intel E1000E是可以用的。另外如果要测试UEFI,只要把BIOS类型选成OVMF(UEFI)即可,不需要创建EFI Disk。
整个PXE流程里,主要涉及这几个玩意:
- DHCP Server:给新来的机器分配ip,仙人指路到tftp下pxe需要的东西
- TFTP Server:用于提供efi文件(UEFI模式)或者pxelinux(Legacy模式),以及相应的引导配置文件
- HTTP Server:用于提供ubuntu的安装.iso和autoinstall用的user-data文件,没啥特殊要求,用nginx或者caddy都行,或者直接python起一个。
- autoinstall:Ubuntu官方的无人值守安装工具,通过一个YAML文件描述安装过程中所有要填的配置项,从而实现完全自动化安装。
dnsmasq 配置
安装dnsmasq用作dhcp server,这个玩意自带了tftp,省事了。
我是直接把家里主路由的DHCP关了,让这家伙独自工作的。如果网络中有其他DHCP server,好像要用Proxy模式,目前还没研究。
apt update
apt install dnsmasq
mkdir /srv/tftp
vim /etc/dnsmasq.conf
# 加一行上游dns resolver
server=server=8.8.8.8
# 编辑pxe配置内容
vim /etc/dnsmasq.d/pxe.conf
pxe.conf文件内容,需要根据对应网络设备和情况来配置网卡,网段等信息
interface=eth0
bind-interfaces
dhcp-range=10.4.0.100,10.4.0.200,255.0.0.0,12h
dhcp-option=option:router,10.0.0.1
enable-tftp
tftp-root=/srv/tftp
dhcp-match=set:bios,option:client-arch,0
dhcp-match=set:uefi64,option:client-arch,7
dhcp-match=set:uefi64,option:client-arch,9
dhcp-boot=tag:bios,pxelinux.0
dhcp-boot=tag:uefi64,bootx64.efi
启动dnsmasq服务,因为可能systemd resolved这个家伙已经把53端口给占了,所以先把它干掉再起dnsmasq。
systemctl stop systemd-resolved
systemctl restart dnsmasq
# 关了防火墙,免得捣乱
systemctl stop ufw
TFTP Server文件准备
UEFI 模式
下载个ubuntu iso然后mount
mount -o loop ubuntu-22.04.5-live-server-amd64.iso /mnt
# 下面的目录在tftp里都是固定的,不能随意改,不然可能找不到文件
cp /mnt/casper/{vmlinuz,initrd} /srv/tftp/
apt download shim-signed
dpkg-deb --fsys-tarfile shim-signed*deb | tar x ./usr/lib/shim/shimx64.efi.signed.latest -O > /srv/tftp/bootx64.efi
apt download grub-efi-amd64-signed
dpkg-deb --fsys-tarfile grub-efi-amd64-signed*deb | tar x ./usr/lib/grub/x86_64-efi-signed/grubnetx64.efi.signed -O > /srv/tftp/grubx64.efi
apt download grub-common
dpkg-deb --fsys-tarfile grub-common*deb | tar x ./usr/share/grub/unicode.pf2 -O > /srv/tftp/unicode.pf2
# grub.cfg放在哪和发行版相关,这玩意应该是焊死在grubx64.efi里的,所以随便放个目录,会导致grub会找不到cfg文件,没法正常引导后续安装
mkdir /srv/tftp/grub
# 编写grub配置文件内容
vim /srv/tftp/grub/grub.cfg
/srv/tftp/grub/grub.cfg 文件内容如下,注意以下几点:
- ds=nocloud-net后面的;前面有个转义符不能忘记
- s=参数后面填的是http server中有user-data这个文件的目录路径
- 命令结尾有---
set default="0"
set timeout=0
if loadfont unicode ; then
set gfxmode=auto
set locale_dir=$prefix/locale
set lang=en_US
fi
terminal_output gfxterm
set menu_color_normal=white/black
set menu_color_highlight=black/light-gray
if background_color 44,0,30; then
clear
fi
function gfxmode {
set gfxpayload="${1}"
if [ "${1}" = "keep" ]; then
set vt_handoff=vt.handoff=7
else
set vt_handoff=
fi
}
set linux_gfx_mode=keep
export linux_gfx_mode
menuentry 'Ubuntu 22.04.5' {
gfxmode $linux_gfx_mode
linux /vmlinuz $vt_handoff ip=dhcp url=http://10.4.0.12:8000/ubuntu-22.04.5-live-server-amd64.iso autoinstall ds=nocloud-net\;s=http://10.4.0.12:8000/ ---
initrd /initrd
}
Legacy BIOS 模式
wget http://archive.ubuntu.com/ubuntu/dists/focal/main/installer-amd64/current/legacy-images/netboot/pxelinux.0
mkdir -p /srv/tftp
mv pxelinux.0 /srv/tftp/
apt install -y syslinux-common
cp /usr/lib/syslinux/modules/bios/ldlinux.c32 /srv/tftp/
mkdir /srv/tftp/pxelinux.cfg
# 编写pxelinux配置
vim /srv/tftp/pxelinux.cfg/default
/srv/tftp/pxelinux.cfg/default 文件内容,需要注意
- ds=nocloud-net后面的;前面没有转义符
- s=参数后面填的是http server中有user-data这个文件的目录路径
- 命令结尾有---
DEFAULT install
LABEL install
KERNEL vmlinuz
INITRD initrd
APPEND root=/dev/ram0 ramdisk_size=1500000 ip=dhcp url=http://10.4.0.12:8000/ubuntu-22.04.5-live-server-amd64.iso autoinstall ds=nocloud-net;s=http://10.4.0.12:8000/ ---
HTTP Server文件准备
先把ubuntu-22.04.5-live-server-amd64.iso放到这个目录下。
然后添加一些autoinstall的配置文件进来。
touch meta-data
vim user-data
user-data文件内容,手写或者从一个安装完的机器/var/log/installer/autoinstall-user-data抄一个过来,配置文件的内容编写参考 https://canonical-subiquity.readthedocs-hosted.com/en/latest/reference/autoinstall-reference.html
注意必须有#cloud-config开头,安装程序才能正确识别和加载
#cloud-config
autoinstall:
version: 1
locale: "en_US.UTF-8"
keyboard:
layout: "us"
variant: ""
identity:
hostname: "new-machine"
username: "eric"
# 用"openssl passwd -6"生成一个
password: "$6$WTiT9hNmg735gtCQ$db6Mkz3V.DF/ymHFR3R1t6/QZ4Gj87v5SladOxKqaxr2XgzQVYcwuXP3I.iBOifNY46EJDEW03zeh.qpNBm.k1"
storage:
layout:
name: direct
network:
version: 2
ethernets:
eth0:
dhcp4: true
ssh:
install-server: true
allow-pw: true
packages:
- vim
- curl
late-commands:
- echo "Autoinstall complete" > /target/root/autoinstall.log
把http server起来
python -m http.server
安装
让机器从网络启动,它在DHCP成功后会自己跑完PXE流程,加载完内核,引导ubuntu安装iso,并通过autoinstall跑完整个安装流程,整个过程不需要任何人工介入。
dnsmasq在有请求时可以看到日志,通过命令查看
journalctl -u dnsmasq -f