Network Booting Operating Systems
Introduction
In this guide, I will show you how to set up a fully functional network boot system that will allow you to run the Live CD’s and installers of multiple different operating systems, as well as several useful maintenance and repair utilities. No USB drives required!
This guide will assume that you have a working grasp of *NIX system administration, familiarity with common Unix utilities, and the ability to configure a working system via a command line.
Rationale
Booting any given operating system is a fairly simple affair: download an ISO or an image file, flash it to a USB drive, and boot from it. If you have an abundance of ISOs, utilities such as Ventoy and YUMI will let you consolidate them all into a single multiboot USB drive. And if you’re especially exotic, you may have one of iodd's excellent drive enclosures that directly mounts ISOs to a virtual SATA optical drive—and can even mount fully rewritable VHD images to discrete virtual SATA LUNs—using the controls on the enclosure itself.
These are all good options, but they all have one common denominator: the requirement of a USB drive. An especially limiting factor if you have lots of systems to work on, but not enough drives for them all!
Last year, I was exposed to network booting for the first time via the excellent FOG Project. And while FOG is geared towards capturing and deploying system images, the experience started me down something of a rabbit hole: wondering if I could take my USB drives full of ISO’s and instead boot them directly off of the network, without needing to constantly dig around for the drives and shuttle them between systems.
The answer, as it turns out, is a resounding "yes"! After lots of experimentation and learning about the network boot abilities of Linux, Windows, and others, I was successful in getting multiple different operating systems to boot over a network connection, exactly as they would via a USB drive.
|
While this project shares a lot in common with the netboot.xyz project—and indeed, is able to boot to it—this project differs in that it operates entirely over a local area network and does not require an Internet connection. As a result, it loads operating systems significantly faster than netboot.xyz does, often at full line speed! |
Requirements
Server
To host our netboot infrastructure, we will need a server with a minimum of:
-
A gigabit Ethernet connection or faster
-
Enough storage space for each OS you plan to run
A NAS is ideal for this setup, but common single-board computers such as the Raspberry Pi or similar is sufficient to host the netboot server.
For the server’s operating system, this guide will cover using FreeBSD. While any Linux or BSD distribution should work as well, you will need to adapt the instructions as necessary for your chosen system. If you have managed to get things working on an alternative operating system, feel free to let me know.
Whichever server OS you choose, it will need to host the following services:
-
TFTP
-
NFS
-
DHCP (in ProxyDHCP mode)
-
Samba (optional, for netbooting Windows-based systems)
iPXE will be used as our network boot software of choice, as it can boot a variety of different operating systems and is very easy to write interactive scripts for.
Network
This guide is designed under the assumption that you will not have control over your local area network, such as in an enterprise network or with common residential and SOHO router boxes. Our netboot server will use a ProxyDHCP server—a separate DHCP server that only responds to PXE clients—to overcome this restriction.
However, if you do have complete control over your network, such as with OpenWrt, Tomato, IPFire, pfSense, OPNsense, or similar, they will allow you to set your network boot parameters directly. This should be preferred wherever possible.
|
The vast majority of PXE clients will work perfectly fine with our default ProxyDHCP setup, but there are some very old or buggy PXE clients that will not work correctly with ProxyDHCP. This is especially true if your network’s primary DHCP server sends conflicting or malformed netboot information of it’s own, which certain residential routers are known to do. Sadly, there is no fix in these situations, outside of switching your network infrastructure over to one of the above options. |
Client
Each client system you plan to boot from the network must have:
-
An Ethernet connection
-
The ability to network boot on said connection
You can enable network booting in the BIOS settings of your client system if it isn’t already. Consult your system or motherboard manual for directions.
The Ethernet connection can be either USB or PCI; as long as your system’s firmware can boot to it, it does not matter.
You do not need to worry about UEFI or BIOS boot modes, either: this netboot setup can serve both types of boot firmware simultaneously.
|
Wi-Fi PXE is not supported. Even if your system has support for it in it’s firmware and can successfully boot to iPXE, there is currently no way to maintain that connection once iPXE hands control over to the operating system. If your system does not have network boot support available, it may be possible to add it into your system by flashing your network card’s boot ROM or installing the UEFI drivers for your network card. Doing so is out of scope for this guide, however. |
Server Installation
|
Other operating systems will be coming soon. Check back later! |
FreeBSD
FreeBSD is a stable, resource-friendly, and performant Unix-like system that, by far, has the easiest time serving as our network boot host. Most of the network services required to run our network boot server—TFTP and NFS in particular—are already included in the base system and are very easy to configure, and the few additional tools we will need to install are similarly very simple to install and configure as well.
Installing FreeBSD
Download the latest release of FreeBSD and boot to the installer on your chosen server system. The installer is very straightforward, so follow all the on-screen steps to install FreeBSD, and reboot to your new installation.
|
A default installation onto either ZFS or UFS is sufficient for our purposes. Further tweaking and configuration of your FreeBSD system is out of scope for this document; refer to the FreeBSD Handbook if you have any special requirements. |
Once rebooted, log in as root.
Configuring FreeBSD
Install the software we will need for our netboot server.
pkg install dnsmasq ipxe
We will configure the software later.
|
FreeBSD includes the |
Configuring Network Services
Before You Begin
|
This guide will use the directory You may of course use whichever directory you wish, but |
Create our netboot directory:
mkdir /netboot
If you have a disk you would like to mount to this directory, do so now and update your fstab accordingly, ensuring it is world readable.
We will be editing scripts as well as downloading and extracting the contents of ISO files into this directory, so you may wish to make /netboot writable by a regular user to avoid the need to obtain root access whenever you wish to add more operating systems.
ProxyDHCP
dnsmasq will be used to provide ProxyDHCP service to the network.
Open the dnsmasq configuration file, located in either:
-
/usr/local/etc/dnsmasq.conf(FreeBSD) -
/etc/dnsmasq.conf(All others)
And populate it with the following lines:
port=0 log-dhcp dhcp-no-override dhcp-range=<ip>,proxy (1)
| 1 | Substitute <ip> with the subnet of your local network, e.g. 192.168.0.0 |
|
The last digit of the IP address does not matter: all that matters is that it is part of the same subnet. If you move your netboot server to a different network, you will need to update this subnet IP appropriately. |
TFTP
In almost all circumstances, dnsmasq’s integrated TFTP server is sufficient. Instructions are provided for different TFTP servers in case you wish to use them, but be warned that they will require additional dnsmasq configuration.
dnsmasq TFTP server
Add the following lines to your dnsmasq.conf file:
enable-tftp tftp-root=/netboot
FreeBSD TFTP server
FreeBSD’s TFTP server is invoked via inetd, so we will need to configure it appropriately.
Open /etc/inetd.conf in your preferred editor, and search for the TFTP service lines:
#tftp dgram udp wait root /usr/libexec/tftpd tftpd -l -s /tftpboot #tftp dgram udp6 wait root /usr/libexec/tftpd tftpd -l -s /tftpboot
Uncomment the IPv4 line and change the TFTP root to /netboot, such that the service line reads as:
tftp dgram udp wait root /usr/libexec/tftpd tftpd -l -s /netboot
PXE
Add the following lines to your dnsmasq.conf file:
dhcp-userclass=set:ipxe,iPXE pxe-prompt=tag:!ipxe,"Press F8 to change iPXE network drivers",3 pxe-service=tag:!ipxe,X86PC,"UNDI driver only",undionly.kpxe pxe-service=tag:!ipxe,X86PC,"Native iPXE drivers",ipxe.pxe pxe-service=tag:!ipxe,X86-64_EFI,"SNP driver only",snponly.efi-x86_64 pxe-service=tag:!ipxe,X86-64_EFI,"Native iPXE drivers",ipxe.efi-x86_64 pxe-service=tag:!ipxe,BC_EFI,"SNP driver only",snponly.efi-x86_64 pxe-service=tag:!ipxe,BC_EFI,"Native iPXE drivers",ipxe.efi-x86_64 pxe-service=tag:!ipxe,IA32_EFI,"SNP driver only",snponly.efi-i386 pxe-service=tag:!ipxe,IA32_EFI,"Native iPXE drivers",ipxe.efi-i386 pxe-service=tag:ipxe,X86PC,"iPXE script",autoexec.ipxe pxe-service=tag:ipxe,X86-64_EFI,"iPXE script",autoexec.ipxe pxe-service=tag:ipxe,BC_EFI,"iPXE script",autoexec.ipxe pxe-service=tag:ipxe,IA32_EFI,"iPXE script",autoexec.ipxe
|
If you’ve chosen to use a different or separate TFTP server, you must add
|
NFS
Next, we will configure NFS.
FreeBSD
Populate /etc/exports with the following:
/netboot -alldirs -webnfs V4: /netboot
Enable Services
Now that our network services are sufficiently configured, it is time to enable them.
FreeBSD
First, enable all of our services:
sysrc dnsmasq_enable="YES" sysrc rpcbind_enable="YES" sysrc rpcbind_flags="-s" sysrc nfs_server_enable="YES" sysrc nfs_server_flags="-t -u" sysrc nfsv4_server_enable="YES" sysrc mountd_enable="YES" sysrc mountd_flags="-r -S" sysrc rpc_lockd_enable="YES" sysrc rpc_statd_enable="YES" sysrc inetd_enable="YES" (1)
| 1 | Only if using FreeBSD’s TFTP daemon |
And then start the services:
service dnsmasq start service rpcbind start service statd start service lockd start service mountd start service nfsd start service inetd start (1)
| 1 | Only if using FreeBSD’s TFTP daemon |
If any services have failed, recheck their configuration and restart them as appropriate.
iPXE
The stock builds of iPXE from the official project website, unfortunately, lack a few crucial features we need: NFS support being chief among them. We will thus go through the steps of getting a correctly configured version of iPXE installed and made available to our netboot clients.
FreeBSD
The customized FreeBSD version of iPXE available in the repos is preconfigured with all of the extra features we will need.
We installed the iPXE package during our configuration of FreeBSD, which added all the required iPXE executables to /usr/local/share/ipxe. Simply copy the needed files from that directory into /netboot:
cp /usr/local/share/ipxe/ipxe.pxe /netboot cp /usr/local/share/ipxe/ipxe.efi-i386 /netboot cp /usr/local/share/ipxe/ipxe.efi-x86_64 /netboot cp /usr/local/share/ipxe/undionly.kpxe /netboot cp /usr/local/share/ipxe/snponly.efi-i386 /netboot cp /usr/local/share/ipxe/snponly.efi-x86_64 /netboot
Writing Initial iPXE Scripts
By itself, iPXE does nothing: it requires a script in order to do anything, and by default, iPXE will attempt to load an autoexec.ipxe script from the root of your TFTP server. We will write this script now.
|
iPXE scripting is very similar to batch scripting and shell scripting. If you know how to write those, you will have a very easy time writing iPXE scripts. If you would like to read more about iPXE scripting beyond the scope of this guide, refer to the iPXE documentation. |
Create autoexec.ipxe in your /netboot directory with the following content:
#!ipxe
iseq ${platform} efi && dhcp ||
chain --autofree --replace ${cwduri}main.ipxe
exit
All this snippet does is ensure the network is configured correctly before loading our main iPXE script, main.ipxe, over TFTP. We will write this next.
Create main.ipxe in your /netboot directory with the following content to start with:
#!ipxe
# Detect CPU arch
cpuid --ext 29 && set arch x86_64 || set arch i386
# ${platform} either "pcbios" or "efi"
# ${next-server} is TFTP IP
set nfs_path /netboot
set nfs_ip ${next-server}
set nfs_url nfs://${nfs_ip}${nfs_path}
:main_menu
menu Choose an OS:
# To be populated later...
item netbootxyz Boot to netboot.xyz (Internet)
item shell iPXE Shell
choose selection && goto ${selection}
## Menus
# To be populated later...
## Others
:netbootxyz
chain --autofree https://boot.netboot.xyz
goto main_menu
:shell
shell
echo Returning to main menu...
sleep 3
goto main_menu
This basic example does a few things:
-
Detects our CPU architecture
-
Sets NFS variables used throughout the scripts
-
Creates the main menu we will be interacting with
-
Adds a few initial entries to the menu for testing
Testing
At this stage, you have done enough setup to test the network boot system. Grab a computer with an Ethernet connection, plug it in, enable it’s network boot capability (if necessary), and boot it to the network.
If you were successful, you should successfully drop into the iPXE menu! If your testing system has Internet connectivity, you can load directly into netboot.xyz using the given menu option, if desired.
Testing with VirtualBox
You can test the netboot setup using a VirtualBox VM, configured as follows:
-
EFI firmware enabled
-
No disks or ISOs attached
-
Using VirtIO networking
-
Virtual network card bridged to your network connection; not using NAT
Configuring a VM like this will allow it to netboot, allowing you to test the setup quickly and easily.
|
Netbooting on a non-EFI VM is possible, but the built-in iPXE firmware that Oracle ships with the VirtualBox BIOS implementation does not work correctly, and will freeze if we try to netboot. If you would like to try anyway, enter the VM settings, uncheck "Enable EFI", check "Network" in the boot order, and switch the network card to a non-VirtIO adapter. Once the VM is started, quickly press Ctrl-B to escape to the iPXE shell when prompted, and execute the following commands: iPXE shell:
dhcp
chain -ar tftp://${proxydhcp/dhcp-server}/ipxe.pxe (1)
This will boot our netboot server’s iPXE executable, which will allow the VM to netboot correctly. |
Adding Operating Systems
Now that your network boot system is finally ready, it’s time to add some operating systems!
Ubuntu (and derivatives)
Installation steps will vary, depending on if you will run the desktop or server live image.
These instructions will assume the latest Ubuntu LTS (24.04.1 as of writing), but any version of Ubuntu will work, provided it has the network drivers for your client system. Make sure to update the directory and file names appropriately!
These instructions will also work the same for Ubuntu spins such as Kubuntu, and derivatives such as Linux Mint and Pop!_OS. Again, make sure to modify the directory and file names as appropriate!
However, for those aforementioned derivatives, the kernel and initrd files may be in different locations and the kernel arguments may be slightly different, so make sure you check the contents of the ISO image and account for any differences!
Desktop
|
These instructions will use the standard Ubuntu Desktop image, but any of the respins like Kubuntu or Xubuntu will work as well. |
Download the latest Ubuntu Desktop and extract the contents to a subdirectory:
mkdir -p /netboot/linux/ubuntu2404desktop cd /netboot/linux/ubuntu2404desktop fetch https://releases.ubuntu.com/24.04.1/ubuntu-24.04.1-desktop-amd64.iso tar xvf ubuntu-24.04.1-desktop-amd64.iso rm ubuntu-24.04.1-desktop-amd64.iso
And then write a script for it in /netboot/linux/ubuntu2404desktop.ipxe:
#!ipxe
set os_root /linux/ubuntu2404desktop
set os_path ${nfs_path}${os_root}
set os_url ${nfs_url}${os_root}
set os_args boot=casper netboot=nfs BOOTIF=${mac} ip=dhcp root=/dev/nfs nfsroot=${nfs_ip}:${os_path} initrd=initrd.magic
set os_kernel ${os_url}/casper/vmlinuz
set os_initrd ${os_url}/casper/initrd
imgfree
clear menu
menu Ubuntu 24.04.1 Desktop:
item stock Boot with default settings
item vga Boot with safe graphics
item --gap ================================================================================
item goback <= Back
choose --default stock --timeout 3000 which_os && goto ${which_os}
:stock
initrd ${os_initrd}
chain ${os_kernel} ${os_args}
exit 0
:vga
initrd ${os_initrd}
chain ${os_kernel} ${os_args} nomodeset
exit 0
:goback
clear menu
exit 0
Add a menu entry for it in your menu.ipxe file (or a subscript of your choosing):
:main_menu
menu Choose an OS:
# To be populated later...
iseq ${arch} x86_64 && item ubuntu2404desktop Ubuntu 24.04.1 Desktop || (1)
item netbootxyz Boot to netboot.xyz (Internet)
item shell iPXE Shell
choose selection && goto ${selection}
## Menus
:ubuntu2404desktop (1)
chain ${nfs_url}/linux/ubuntu2404desktop.ipxe (1)
goto main_menu (1)
| 1 | Add these lines to your config. |
You should now be able to network boot Ubuntu 24.04 Desktop!
Server
Download the latest Ubuntu Server and extract the contents to a subdirectory:
mkdir -p /netboot/linux/ubuntu2404server cd /netboot/linux/ubuntu2404server fetch https://releases.ubuntu.com/24.04.1/ubuntu-24.04.1-live-server-amd64.iso tar xvf ubuntu-24.04.1-live-server-amd64.iso rm ubuntu-24.04.1-live-server-amd64.iso
And then write a script for it in /netboot/linux/ubuntu2404server.ipxe:
#!ipxe
set os_root /os/linux/ubuntu-24.04.1-live-server-amd64
set os_path ${nfs_path}${os_root}
set os_url ${nfs_url}${os_root}
set os_args netboot=nfs BOOTIF=${mac} ip=dhcp root=/dev/nfs nfsroot=${nfs_ip}:${os_path} initrd=initrd.magic
set os_kernel ${os_url}/casper/vmlinuz
set os_initrd ${os_url}/casper/initrd
imgfree
clear menu
menu Ubuntu 24.04.1 Server:
item stock Boot with default settings
item vga Boot with safe graphics
item --gap ================================================================================
item goback <= Back
choose --default stock --timeout 3000 which_os && goto ${which_os}
:stock
initrd ${os_initrd}
chain ${os_kernel} ${os_args}
exit 0
:vga
initrd ${os_initrd}
chain ${os_kernel} ${os_args} nomodeset
exit 0
:goback
clear menu
exit 0
Add a menu entry for it in your menu.ipxe file (or a subscript of your choosing):
:main_menu
menu Choose an OS:
# To be populated later...
iseq ${arch} x86_64 && item ubuntu2404server Ubuntu 24.04.1 Server || (1)
item netbootxyz Boot to netboot.xyz (Internet)
item shell iPXE Shell
choose selection && goto ${selection}
## Menus
:ubuntu2404server (1)
chain ${nfs_url}/linux/ubuntu2404server.ipxe (1)
goto main_menu (1)
| 1 | Add these lines to your config. |
You should now be able to network boot Ubuntu 24.04 Server!
Debian (and derivatives)
|
Currently, only the live Debian images can be network booted. The standard Debian installer images will boot, but they will not mount the NFS share, thus falling back to acting as netinstall images and defeating the entire purpose of netbooting them. I am currently investigating how to fix this, and welcome any suggestions! |
These instructions will assume the latest version of Debian (12.7 as of writing), but any version of Debian will work, provided it has the network drivers for your client system. Make sure to update the directory and file names appropriately!
These instructions will also work the same for Debian distros such as LMDE and MX Linux. However, kernel and initrd files and boot arguments may be different on these distributions, so make sure you check the ISO contents and adjust as needed!
Live
|
These instructions will use the live GNOME image of Debian, but any of the live versions will work, including the command-line only 'standard' image. |
Download the latest Debian Live image and extract the contents to a subdirectory:
mkdir -p /netboot/linux/debian12gnome cd /netboot/linux/debian12gnome fetch https://cdimage.debian.org/debian-cd/current-live/amd64/iso-hybrid/debian-live-12.7.0-amd64-gnome.iso tar xvf debian-live-12.7.0-amd64-gnome.iso rm debian-live-12.7.0-amd64-gnome.iso
And then write a script for it in /netboot/linux/debian12gnome.ipxe:
#!ipxe
set os_root /linux/debian12gnome
set os_path ${nfs_path}${os_root}
set os_url ${nfs_url}${os_root}
set os_args boot=live components BOOTIF=${mac} ip=dhcp root=/dev/nfs nfsroot=${nfs_ip}:${os_path} initrd=initrd.magic
set os_kernel ${os_url}/live/vmlinuz
set os_initrd ${os_url}/live/initrd.img
imgfree
clear menu
menu Debian Live 12.7.0 amd64 (GNOME):
item stock Boot with default settings
item failsafe Boot in failsafe mode
item --gap ================================================================================
item goback <= Back
choose --default stock --timeout 3000 which_os && goto ${which_os}
:stock
initrd ${os_initrd}
chain ${os_kernel} ${os_args}
exit 0
:failsafe
initrd ${os_initrd}
chain ${os_kernel} ${os_args} memtest noapic noapm nodma nomce nosmp nosplash vga=788
exit 0
:goback
clear menu
exit 0
Add a menu entry for it in your menu.ipxe file (or a subscript of your choosing):
:main_menu
menu Choose an OS:
# To be populated later...
iseq ${arch} x86_64 && item debian12gnome Debian 12 Live (GNOME) || (1)
item netbootxyz Boot to netboot.xyz (Internet)
item shell iPXE Shell
choose selection && goto ${selection}
## Menus
:debian12gnome (1)
chain ${nfs_url}/linux/debian12gnome.ipxe (1)
goto main_menu (1)
| 1 | Add these lines to your config. |
You should now be able to network boot the Debian 12 live system!
Alma/Rocky Linux
Both the installers and live images of Alma/Rocky Linux 8 and 9 are fully bootable over the network.
The setup required for Alma/Rocky Linux 8 and 9 is largely identical, but the kernel arguments differ between the installer and live images.
Installer
|
This example will use the AlmaLinux 9 DVD image, but the minimal image may be used instead, if desired. Only the names and URLs need to be modified to adapt these instructions to AlmaLinux 8, or the equivalent Rocky Linux releases. |
Download the latest AlmaLinux and extract the contents to a subdirectory:
mkdir -p /netboot/linux/alma9install cd /netboot/linux/alma9install fetch https://repo.almalinux.org/almalinux/9.4/isos/x86_64/AlmaLinux-9.4-x86_64-dvd.iso tar xvf AlmaLinux-9.4-x86_64-dvd.iso rm AlmaLinux-9.4-x86_64-dvd.iso
And then write a script for it in /netboot/linux/alma9install.ipxe:
#!ipxe
set os_root /linux/alma9install
set os_path ${nfs_path}${os_root}
set os_url ${nfs_url}${os_root}
set os_args inst.stage2=nfs:${nfs_ip}:${os_path} inst.repo=nfs:${nfs_ip}:${os_path} initrd=initrd.magic
set os_kernel ${os_url}/images/pxeboot/vmlinuz
set os_initrd ${os_url}/images/pxeboot/initrd.img
imgfree
clear menu
menu AlmaLinux 9 Installer:
item stock Boot with default settings
item textonly Boot into text mode
item rescue Boot into rescue mode
item --gap ================================================================================
item goback <= Back
choose --default stock --timeout 3000 which_os && goto ${which_os}
:stock
initrd ${os_initrd}
chain ${os_kernel} ${os_args}
exit 0
:textonly
initrd ${os_initrd}
chain ${os_kernel} ${os_args} inst.text
exit 0
:rescue
initrd ${os_initrd}
chain ${os_kernel} ${os_args} inst.rescue
exit 0
:goback
clear menu
exit 0
Add a menu entry for it in your menu.ipxe file (or a subscript of your choosing):
:main_menu
menu Choose an OS:
# To be populated later...
iseq ${arch} x86_64 && item alma9install AlmaLinux 9 Installer || (1)
item netbootxyz Boot to netboot.xyz (Internet)
item shell iPXE Shell
choose selection && goto ${selection}
## Menus
:alma9install (1)
chain ${nfs_url}/linux/alma9install.ipxe (1)
goto main_menu (1)
| 1 | Add these lines to your config. |
You should now be able to network boot the AlmaLinux 9 installer!
Live
|
This example will use the full AlmaLinux 9 live GNOME image, but any of the available live environments will work. As before, only the names and URLs need to be modified to adapt these instructions to AlmaLinux 8, or the equivalent Rocky Linux releases. |
Download the latest AlmaLinux and extract the contents to a subdirectory:
mkdir -p /netboot/linux/alma9live cd /netboot/linux/alma9live fetch https://repo.almalinux.org/almalinux/9/live/x86_64/AlmaLinux-9.4-x86_64-Live-GNOME.iso tar xvf AlmaLinux-9.4-x86_64-Live-GNOME.iso rm AlmaLinux-9.4-x86_64-Live-GNOME.iso
And then write a script for it in /netboot/linux/alma9live.ipxe:
#!ipxe
set os_root /linux/alma9live
set os_path ${nfs_path}${os_root}
set os_url ${nfs_url}${os_root}
set os_args inst.stage2=nfs:${nfs_ip}:${os_path} inst.repo=nfs:${nfs_ip}:${os_path} initrd=initrd.magic
set os_kernel ${os_url}/images/pxeboot/vmlinuz
set os_initrd ${os_url}/images/pxeboot/initrd.img
imgfree
clear menu
menu AlmaLinux 9 Live (GNOME):
item stock Boot with default settings
item --gap ================================================================================
item goback <= Back
choose --default stock --timeout 3000 which_os && goto ${which_os}
:stock
initrd ${os_initrd}
chain ${os_kernel} ${os_args}
exit 0
:goback
clear menu
exit 0
Add a menu entry for it in your menu.ipxe file (or a subscript of your choosing):
:main_menu
menu Choose an OS:
# To be populated later...
iseq ${arch} x86_64 && item alma9live AlmaLinux 9 Live (GNOME) || (1)
item netbootxyz Boot to netboot.xyz (Internet)
item shell iPXE Shell
choose selection && goto ${selection}
## Menus
:alma9live (1)
chain ${nfs_url}/linux/alma9live.ipxe (1)
goto main_menu (1)
| 1 | Add these lines to your config. |
You should now be able to network boot the AlmaLinux 9 live system!
Arch Linux
Arch Linux is fairly straightforward to network boot.
Download the latest Arch ISO and extract the contents to a subdirectory:
mkdir -p /netboot/linux/archlinux cd /netboot/linux/archlinux fetch https://geo.mirror.pkgbuild.com/iso/2024.10.01/archlinux-x86_64.iso tar xvf archlinux-x86_64.iso rm archlinux-x86_64.iso
And then write a script for it in /netboot/linux/archlinux.ipxe:
#!ipxe
set os_root /linux/archlinux
set os_path ${nfs_path}${os_root}
set os_url ${nfs_url}${os_root}
set os_args BOOTIF=${mac} ip=dhcp archisobasedir=arch archiso_nfs_srv=${nfs_ip}:${os_path} initrd=initrd.magic
set os_kernel ${os_url}/arch/boot/x86_64/vmlinuz-linux
set os_initrd ${os_url}/arch/boot/x86_64/initramfs-linux.img
imgfree
clear menu
menu Arch Linux:
item stock Boot with default settings
item noverify Boot without signature verification
item nocopy Boot in low RAM mode
item nocpver Boot in low RAM mode & without signature verification
item --gap ================================================================================
item goback <= Back
choose --default stock --timeout 3000 which_os && goto ${which_os}
:stock
initrd ${os_initrd}
chain ${os_kernel} ${os_args} cms_verify=y
exit 0
:noverify
initrd ${os_initrd}
chain ${os_kernel} ${os_args}
exit 0
:nocopy
initrd ${os_initrd}
chain ${os_kernel} ${os_args} copytoram=n cms_verify=y
exit 0
:nocpver
initrd ${os_initrd}
chain ${os_kernel} ${os_args} copytoram=n
exit 0
:goback
clear menu
exit 0
Add a menu entry for it in your menu.ipxe file (or a subscript of your choosing):
:main_menu
menu Choose an OS:
# To be populated later...
iseq ${arch} x86_64 && item archlinux Arch Linux || (1)
item netbootxyz Boot to netboot.xyz (Internet)
item shell iPXE Shell
choose selection && goto ${selection}
## Menus
:archlinux (1)
chain ${nfs_url}/linux/archlinux.ipxe (1)
goto main_menu (1)
| 1 | Add these lines to your config. |
You should now be able to network boot into the Arch Linux installer!
Adding Utilities
Beyond just operating systems, you can also network boot a variety of useful system utilities.
UEFI Shells
If your system doesn’t have it’s own UEFI shell, having one available via the network can come in very handy.
This section will cover obtaining both an upstream EDK2 build of the shell, and the patched, widely compatible shell from OpenCore.
mkdir -p /netboot/util/uefishell cd /netboot/util/uefishell fetch https://github.com/pbatard/UEFI-Shell/releases/download/24H1/shellia32.efi fetch https://github.com/pbatard/UEFI-Shell/releases/download/24H1/shellx64.efi fetch https://github.com/acidanthera/OpenCorePkg/releases/download/1.0.2/OpenCore-1.0.2-RELEASE.zip tar xvf OpenCore-1.0.2-RELEASE.zip X64/EFI/OC/Tools/OpenShell.efi IA32/EFI/OC/Tools/OpenShell.efi mv X64/EFI/OC/Tools/OpenShell.efi openshellx64.efi mv IA32/EFI/OC/Tools/OpenShell.efi openshellia32.efi rm -r X64 IA32 OpenCore-1.0.2-RELEASE.zip
With the shells downloaded, write an iPXE script /netboot/util/uefishell.ipxe to boot them:
#!ipxe
set os_root /util/misc/uefishell
set os_url ${nfs_url}${os_root}
imgfree
clear menu
iseq ${arch} x86_64 && goto menu64 ||
iseq ${arch} i386 && goto menu32 ||
echo Arch not supported, returning...
sleep 2
goto goback
:menu64
menu UEFI Shells (64-bit):
item edk64 EDK2 Shell ||
item open64 OpenCore Shell ||
item --gap ================================================================================
item goback <= Back
choose --default edk64 --timeout 3000 uefishell && goto ${uefishell}
:menu32
menu UEFI Shells (32-bit):
item edk32 EDK2 Shell ||
item open32 OpenCore Shell ||
item --gap ================================================================================
item goback <= Back
choose --default edk32 --timeout 3000 uefishell && goto ${uefishell}
:edk64
chain ${os_url}/shellx64.efi
exit 0
:open64
chain ${os_url}/openshellx64.efi
exit 0
:edk32
chain ${os_url}/shellia32.efi
exit 0
:open32
chain ${os_url}/openshellia32.efi
exit 0
:goback
clear menu
exit 0
Add a menu entry for it in your menu.ipxe file (or a subscript of your choosing):
:main_menu
menu Choose an OS:
# To be populated later...
iseq ${platform} efi && item uefishell UEFI Shell || (1)
item netbootxyz Boot to netboot.xyz (Internet)
item shell iPXE Shell
choose selection && goto ${selection}
## Menus
:uefishell (1)
chain ${nfs_url}/util/uefishell.ipxe (1)
goto main_menu (1)
| 1 | Add these lines to your config. |
You should now be able to network boot to a UEFI shell!
rEFInd
rEFInd is a very useful UEFI boot manager that can help you reboot into your OS if your bootloader becomes damaged somehow.
We can load it over PXE as well, but with the small caveat that it will be in text mode, as we cannot load rEFInd’s graphical assets over the network as well. This should not matter, as rEFInd remains perfectly usable in text mode.
mkdir -p /netboot/util/refind cd /netboot/util/refind fetch http://sourceforge.net/projects/refind/files/0.14.2/refind-bin-0.14.2.zip tar xvf refind-bin-0.14.2.zip rm refind-bin-0.14.2.zip sed s/#textonly/textonly/ refind-bin-0.14.2/refind/refind.conf-sample > refind-bin-0.14.2/refind/refind.conf-pxe
Now write the iPXE script for rEFInd under /netboot/util/refind.ipxe:
#!ipxe
set os_root /util/refind/refind-bin-0.14.2/refind
set os_url ${nfs_url}${os_root}
imgfree
clear menu
iseq ${arch} x86_64 && goto menu64 ||
iseq ${arch} i386 && goto menu32 ||
echo Arch not supported, returning...
sleep 2
goto goback
:menu64
menu rEFInd (64-bit):
item stock64 Boot with default settings
item drv64 Boot with extra filesystem drivers
item --gap ================================================================================
item goback <= Back
choose --default stock64 --timeout 3000 refind && goto ${refind}
:menu32
menu rEFInd (32-bit):
item stock32 Boot with default settings
item drv32 Boot with extra filesystem drivers
item --gap ================================================================================
item goback <= Back
choose --default stock32 --timeout 3000 refind && goto ${refind}
:stock64
initrd ${os_url}/refind.conf-pxe
chain ${os_url}/refind_x64.efi
exit 0
:drv64
initrd ${os_url}/refind.conf-pxe
initrd ${os_url}/drivers_x64/btrfs_x64.efi
initrd ${os_url}/drivers_x64/ext4_x64.efi
initrd ${os_url}/drivers_x64/hfs_x64.efi
initrd ${os_url}/drivers_x64/iso9660_x64.efi
chain ${os_url}/refind_x64.efi
exit 0
:stock32
initrd ${os_url}/refind.conf-pxe
chain ${os_url}/refind_ia32.efi
exit 0
:drv32
initrd ${os_url}/refind.conf-pxe
initrd ${os_url}/drivers_ia32/btrfs_ia32.efi
initrd ${os_url}/drivers_ia32/ext4_ia32.efi
initrd ${os_url}/drivers_ia32/hfs_ia32.efi
initrd ${os_url}/drivers_ia32/iso9660_ia32.efi
chain ${os_url}/refind_ia32.efi
exit 0
:goback
clear menu
exit 0
Add a menu entry for it in your menu.ipxe file (or a subscript of your choosing):
:main_menu
menu Choose an OS:
# To be populated later...
iseq ${platform} efi && item refind rEFInd || (1)
item netbootxyz Boot to netboot.xyz (Internet)
item shell iPXE Shell
choose selection && goto ${selection}
## Menus
:refind (1)
chain ${nfs_url}/util/refind.ipxe (1)
goto main_menu (1)
| 1 | Add these lines to your config. |
You should now be able to network boot rEFInd!
Memtest86+
Memtest86+ is a powerful open-source memory tester for PC’s. It has explicit support for PXE booting, and loading it via iPXE allows us to specify extra command-line options for it, just like in the GRUB distribution of Memtest86+.
|
Memtest86+ is not to be confused with Memtest86, a commercial product with a very similar name. While the two share a common ancestry and perform a similar function, the commercial Memtest86 requires a $5000 site license in order for it to PXE boot, and will thus not be covered in this guide. |
mkdir -p /netboot/util/memtest86 cd /netboot/util/memtest86 fetch https://memtest.org/download/v7.00/mt86plus_7.00.binaries.zip tar xvf mt86plus_7.00.binaries.zip rm mt86plus_7.00.binaries.zip
Now write the iPXE script for Memtest86+ under /netboot/util/memtest86.ipxe:
#!ipxe
set os_path /util/memtest86
set os_url ${nfs_url}${os_path}
imgfree
clear menu
menu Memtest86+:
item stock Boot with default settings
item newkb Boot with built-in USB keyboard support
item oldkb Boot with legacy BIOS emulation for USB keyboards
item nosmp Boot without SMP & memory detection
item --gap ================================================================================
item back2test <= Back to System Tests
choose --default stock --timeout 3000 mtargs
iseq ${mtargs} back2test && goto back2test ||
iseq ${mtargs} stock && clear os_args ||
iseq ${mtargs} newkb && set os_args keyboard=both ||
iseq ${mtargs} oldkb && set os_args keyboard=legacy ||
iseq ${mtargs} nosmp && set os_args nosmp nosm nobench ||
iseq ${platform} efi && iseq ${arch} x86_64 && kernel ${os_url}/memtest64.efi ${os_args} ||
iseq ${platform} efi && iseq ${arch} i386 && kernel ${os_url}/memtest32.efi ${os_args} ||
iseq ${platform} pcbios && iseq ${arch} x86_64 && kernel ${os_url}/memtest64.bin ${os_args} ||
iseq ${platform} pcbios && iseq ${arch} i386 && kernel ${os_url}/memtest32.bin ${os_args} ||
chain || goto noarch
:back2test
clear menu
exit 0
:noarch
echo No Memtest86+ version for your architecture. Returning to previous menu...
sleep 2
clear menu
exit 0
Add a menu entry for it in your menu.ipxe file (or a subscript of your choosing):
:main_menu
menu Choose an OS:
# To be populated later...
item memtest86 Memtest86+ (1)
item netbootxyz Boot to netboot.xyz (Internet)
item shell iPXE Shell
choose selection && goto ${selection}
## Menus
:memtest86 (1)
chain ${nfs_url}/util/memtest86.ipxe (1)
goto main_menu (1)
| 1 | Add these lines to your config. |
You should now be able to network boot Memtest86+!
Future Expansion
Further revisions and additions to this guide will include:
-
Setting up the netboot server on Alma/Rocky Linux
-
Network booting even more systems, including:
-
OpenSUSE
-
Linux Mint
-
Pop!_OS
-
Microsoft Windows installer
-
Hiren’s Boot CD
-
PlopKexec
-
ZFSBootMenu
-
Other miscellaneous utilities
-
Errata
-
1.2
-
Metadata edits for Jekyll processing.
-
-
1.1 - 2024-12-14
-
Updated copyright to CC-BY.
-
Minor edits and cleanup.
-
Future entries were expanded upon, but remain commented out for the time being.
-
-
1.0 - 2024-10-25
-
Initial release
-