From 62f79d91f894e828510b181c49f3f84b98ee036c Mon Sep 17 00:00:00 2001 From: Tom Elliott Date: Tue, 18 Aug 2026 12:02:44 -0500 Subject: [PATCH 1/2] autoexec.ipxe is how UEFI boots now, not an opt-in FOG 1.6.1 builds every UEFI binary without its iPXE boot script compiled in, so each one downloads autoexec.ipxe and runs it. The autoexec/ folder that used to hold the script-less duplicates is gone -- the root binaries ARE that build now -- and the installer removes it on upgrade. That inverts what these pages describe, so the DHCP page's "The autoexec/ boot files (UEFI only)" section is replaced rather than amended, with an upgrade note carrying the old-path -> new-path table. A DHCP filename beginning "autoexec/" stops resolving, and TFTP answers a missing file with an error most firmware renders as a generic PXE failure -- nothing in it points the reader here, so the mapping has to be findable from the symptom. Documents --boot-delay while there, including the part that is easy to get wrong: it edits autoexec.ipxe, so it does nothing for legacy BIOS, whose script is still compiled in. A non-zero delay makes FOG's generated DHCP config point BIOS clients at 10secdelay/ instead, and that build is exactly ten seconds whatever value was passed. Secure Boot pages corrected on three points that are now wrong rather than merely incomplete: - the hard-link set is the TFTP root, i386-efi/, arm64-efi/, secureboot/ and secureboot/arm64-efi/ -- five paths, not six, and no autoexec/ among them. Verified against a 1.6.1 server: one inode, links=5. - the repair one-liner pointed at /tftpboot/autoexec/autoexec.ipxe, which no longer exists. - "FOG's own build -- the boot script compiled in, no signature" was true of both halves and is now true of neither. FOG's build reads autoexec.ipxe like upstream's does, and on a server with Secure Boot keys it carries FOG's own signature. What actually separates the two files is which trust root the client must have enrolled, so say that instead. translations/ is left alone: docs/ is the source of truth and translate.yml regenerates it, which is the repo's existing arrangement. --- .../network-setup/dhcp-server-settings.md | 96 +++++++++++++------ docs/kb/how-tos/secure-boot-signing.md | 7 +- .../secure-boot-technical-details.md | 28 +++--- 3 files changed, 87 insertions(+), 44 deletions(-) diff --git a/docs/installation/network-setup/dhcp-server-settings.md b/docs/installation/network-setup/dhcp-server-settings.md index 81ca19a5..a43ba9a1 100644 --- a/docs/installation/network-setup/dhcp-server-settings.md +++ b/docs/installation/network-setup/dhcp-server-settings.md @@ -59,43 +59,81 @@ For older legacy models, these are the boot files to set You can find other pxe boot files in you `/tftpboot` directory on your fogserver. -### The `autoexec/` boot files (UEFI only) +### How UEFI clients get their boot script -Alongside the files above, FOG ships a second set of UEFI binaries in -`/tftpboot/autoexec/`. They are built from identical source, with one -difference: the iPXE boot script is **not** compiled into the binary. Instead -they download a plain text script — `autoexec.ipxe` — over TFTP from the same -folder they were loaded from, and run that. +Every UEFI binary FOG ships is built **without** its iPXE boot script compiled +in. Each one downloads a plain text script — `autoexec.ipxe` — over TFTP from +the folder it was loaded from, and runs that. -The practical benefit is that the boot logic becomes a file you can edit on the +The practical benefit is that the boot logic is a file you can edit on the server. Changing something like the menu timeout means editing -`/tftpboot/autoexec/autoexec.ipxe`, not rebuilding binaries. +`/tftpboot/autoexec.ipxe`, not rebuilding binaries. It is also the only shape +that works under UEFI Secure Boot, where a compiled-in script is not permitted. -To use them, prefix the file name in option 67 with `autoexec/`: +A copy of `autoexec.ipxe` sits in every folder holding a UEFI binary — the +`/tftpboot` root, `i386-efi/`, `arm64-efi/` and the `secureboot/` tree. They are +hard links to one file, so editing any of them edits all of them. -* `autoexec/snponly.efi` -* `autoexec/ipxe.efi` -* `autoexec/i386-efi/snponly.efi` -* `autoexec/arm64-efi/snponly.efi` - -Option 66 does not change. +Nothing about option 66 or option 67 changes for this. Point option 67 at +`snponly.efi`, `i386-efi/snponly.efi` and so on exactly as above. > [!warning] -> **This works for UEFI clients only.** Legacy BIOS boot files -> (`undionly.kpxe`, `undionly.kkpxe`, `ipxe.kpxe`, `ipxe.kkpxe`) cannot use it. -> The mechanism that fetches `autoexec.ipxe` exists only in iPXE's EFI startup -> path; there is no BIOS equivalent, so a BIOS binary would simply ignore the -> file. This is why no BIOS boot files are shipped in `autoexec/` — a copy there -> would boot, but only because it still has the script compiled in, which makes -> it look like the mechanism works for BIOS when it does not. -> -> In a mixed environment, keep BIOS clients pointed at the root -> (`undionly.kpxe`) and use `autoexec/` only for the UEFI classes. +> **Legacy BIOS works the other way round.** BIOS boot files +> (`undionly.kpxe`, `undionly.kkpxe`, `ipxe.kpxe`, `ipxe.kkpxe`) still have +> their script compiled in, and they ignore `autoexec.ipxe` entirely — the +> mechanism that fetches it exists only in iPXE's EFI startup path. Editing +> `autoexec.ipxe` changes nothing for a BIOS client. + +#### Upgrading from FOG 1.6.0 or earlier: the `autoexec/` folder is gone + +Earlier releases shipped a *second*, opt-in set of UEFI binaries in +`/tftpboot/autoexec/` — those were the ones without a compiled-in script, and +the files in the root had one. That is now the other way round: the root binaries +are the script-less ones, so the duplicate folder served no purpose and the +installer removes it. + +**If any DHCP server hands out a boot filename beginning `autoexec/`, drop that +prefix.** The file at the new path is the same build: + +| Old | New | +|---|---| +| `autoexec/snponly.efi` | `snponly.efi` | +| `autoexec/ipxe.efi` | `ipxe.efi` | +| `autoexec/i386-efi/snponly.efi` | `i386-efi/snponly.efi` | +| `autoexec/arm64-efi/snponly.efi` | `arm64-efi/snponly.efi` | + +The installer cannot fix this for you, because the DHCP server handing out that +name is often not the FOG server. Left unchanged, the client asks for a file +that no longer exists and TFTP answers with an error most firmware renders as a +generic PXE failure, with nothing in it to point you here. + +### Adding a delay before the first DHCP attempt -Both sets are installed and kept in step with each other. The files in the root -of `/tftpboot` remain the default and are what every existing FOG install uses; -`autoexec/` is opt-in and behaves identically otherwise. If you are not sure -which you want, use the root files. +Some switches take several seconds to bring a port out of STP listening or out +of powersave, and iPXE's first DHCP request goes out before that — which looks +like an intermittent "no DHCP answer" at boot. + +Pass `--boot-delay` to the installer to insert a sleep, in seconds, at the top +of `autoexec.ipxe`: + +```bash +./installfog.sh --boot-delay 10 +``` + +The setting is remembered across upgrades. `--boot-delay 0` removes it again. + +> [!note] +> **Legacy BIOS needs a different boot file for this, not the option.** With its +> script compiled in there is nothing to edit, so the delay has to be a separate +> build: that is what `/tftpboot/10secdelay/` holds. Setting a non-zero +> `--boot-delay` makes FOG's generated DHCP configuration point BIOS clients +> there automatically. That build is exactly ten seconds — no other value exists +> — so `--boot-delay 7` gives UEFI clients seven seconds and BIOS clients ten, +> and the installer says so when it runs. +> +> `/tftpboot/10secdelay/` holds BIOS files only. Booting a UEFI binary from +> there would hang the client, which is why FOG 1.6.1 removes any left over from +> an earlier release. ## Examples of DHCP server configurations diff --git a/docs/kb/how-tos/secure-boot-signing.md b/docs/kb/how-tos/secure-boot-signing.md index 4e975912..5e269918 100644 --- a/docs/kb/how-tos/secure-boot-signing.md +++ b/docs/kb/how-tos/secure-boot-signing.md @@ -287,9 +287,10 @@ certificate table, an unsigned one does not: sbverify --list /tftpboot/secureboot/snponly.efi ``` -The signer should be **iPXE Secure Boot Intermediate G1A**. FOG's own -`/tftpboot/ipxe.efi` and `/tftpboot/autoexec/snponly.efi` have no signature at -all — if you see that, you are looking at the wrong file. +The signer should be **iPXE Secure Boot Intermediate G1A**. FOG's own builds +in the TFTP root — `/tftpboot/ipxe.efi`, `/tftpboot/snponly.efi` — are either +unsigned or signed by **FOG Project Secure Boot Signing**, this server's own +key. Either of those means you are looking at the wrong file. On arm64 the equivalents are `arm64-efi/snponly-shimaa64.efi` and `arm64-efi/snponly.efi`. diff --git a/docs/kb/reference/secure-boot-technical-details.md b/docs/kb/reference/secure-boot-technical-details.md index 50eeedb1..3173cffa 100644 --- a/docs/kb/reference/secure-boot-technical-details.md +++ b/docs/kb/reference/secure-boot-technical-details.md @@ -36,7 +36,9 @@ both binaries already carry signatures the firmware and shim trust. >front and the signature on the kernel. Because upstream's `snponly.efi` has no boot script compiled in, it fetches one -over TFTP, and **where it looks is not a single fixed path**. iPXE asks for the +over TFTP, and **where it looks is not a single fixed path**. Since FOG 1.6.1 +this is true of *every* UEFI binary FOG ships, not just upstream's — none of +them embed a script any more. iPXE asks for the bare name `autoexec.ipxe` and tries two locations in order: 1. relative to its *current working URI* — the TFTP directory the running @@ -51,10 +53,10 @@ autoexec.ipxe... Not found ``` The installer satisfies both. It hard-links `autoexec.ipxe` into every -directory an EMBED-less binary can be booted from — the TFTP root, -`autoexec/`, `autoexec/i386-efi/`, `autoexec/arm64-efi/`, `secureboot/` and -`secureboot/arm64-efi/`. All six are one file, so editing any of them changes -all of them and there is no copy left quietly running the old script. +directory a script-less binary can be booted from — the TFTP root, +`i386-efi/`, `arm64-efi/`, `secureboot/` and `secureboot/arm64-efi/`. All five +are one file, so editing any of them changes all of them and there is no copy +left quietly running the old script. A hard link rather than a symlink because some TFTP daemons refuse to follow symlinks, while a hard link is indistinguishable from a regular file to all of @@ -64,11 +66,11 @@ If a link has been broken — an older install, or the file was replaced by an editor that writes-and-renames — re-running the installer restores it, or: ```bash -sudo ln -f /tftpboot/autoexec/autoexec.ipxe /tftpboot/secureboot/autoexec.ipxe +sudo ln -f /tftpboot/autoexec.ipxe /tftpboot/secureboot/autoexec.ipxe ``` You can check they really are one file: every copy should report the same -inode and a link count of 6. +inode and a link count of 5. ```bash find /tftpboot -name autoexec.ipxe -printf '%i links=%n %p\n' @@ -84,11 +86,13 @@ at the TFTP root, and non-Secure-Boot machines keep booting it. The signed copy lives under `secureboot/` and is reached only by machines you point there. >[!note] Both files are called `snponly.efi`, and that is fine ->`/tftpboot/snponly.efi` is FOG's own build — the boot script compiled in, no ->signature. `/tftpboot/secureboot/snponly.efi` is upstream's signed build, ->which reads its script from `autoexec.ipxe` instead. They are different ->binaries doing the same job by different means, which is why the signed one ->gets its own directory rather than replacing the other. +>`/tftpboot/snponly.efi` is FOG's own build. `/tftpboot/secureboot/snponly.efi` +>is upstream's, signed by the iPXE project. Both read their script from +>`autoexec.ipxe`; what differs is who vouches for the binary — upstream's is +>trusted through shim and Microsoft's key, FOG's through the MOK this server +>publishes. That is why the signed one gets its own directory rather than +>replacing the other, and which you point DHCP at decides which trust root the +>client has to have enrolled. ### If the chain loads but the network never comes up From 7557c4de67bd8039d03012d4b12e6031afaa97fc Mon Sep 17 00:00:00 2001 From: Tom Elliott Date: Tue, 18 Aug 2026 13:13:27 -0500 Subject: [PATCH 2/2] Correct the release these changes land in No 1.6.x tag exists yet -- 1.6.0 has never been released, so "FOG 1.6.1 removes ..." pointed readers at a release that does not exist, and "upgrading from 1.6.0 or earlier" described an upgrade nobody can be doing. The autoexec/ folder only ever shipped in 1.6.0 betas, and all of this lands in 1.6.0 itself. Co-Authored-By: Claude --- docs/installation/network-setup/dhcp-server-settings.md | 8 ++++---- docs/kb/reference/secure-boot-technical-details.md | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/docs/installation/network-setup/dhcp-server-settings.md b/docs/installation/network-setup/dhcp-server-settings.md index a43ba9a1..31749949 100644 --- a/docs/installation/network-setup/dhcp-server-settings.md +++ b/docs/installation/network-setup/dhcp-server-settings.md @@ -84,9 +84,9 @@ Nothing about option 66 or option 67 changes for this. Point option 67 at > mechanism that fetches it exists only in iPXE's EFI startup path. Editing > `autoexec.ipxe` changes nothing for a BIOS client. -#### Upgrading from FOG 1.6.0 or earlier: the `autoexec/` folder is gone +#### Upgrading from a 1.6.0 beta: the `autoexec/` folder is gone -Earlier releases shipped a *second*, opt-in set of UEFI binaries in +Earlier 1.6.0 betas shipped a *second*, opt-in set of UEFI binaries in `/tftpboot/autoexec/` — those were the ones without a compiled-in script, and the files in the root had one. That is now the other way round: the root binaries are the script-less ones, so the duplicate folder served no purpose and the @@ -132,8 +132,8 @@ The setting is remembered across upgrades. `--boot-delay 0` removes it again. > and the installer says so when it runs. > > `/tftpboot/10secdelay/` holds BIOS files only. Booting a UEFI binary from -> there would hang the client, which is why FOG 1.6.1 removes any left over from -> an earlier release. +> there would hang the client, which is why the installer removes any left over +> from an earlier beta. ## Examples of DHCP server configurations diff --git a/docs/kb/reference/secure-boot-technical-details.md b/docs/kb/reference/secure-boot-technical-details.md index 3173cffa..d0ba573e 100644 --- a/docs/kb/reference/secure-boot-technical-details.md +++ b/docs/kb/reference/secure-boot-technical-details.md @@ -36,7 +36,7 @@ both binaries already carry signatures the firmware and shim trust. >front and the signature on the kernel. Because upstream's `snponly.efi` has no boot script compiled in, it fetches one -over TFTP, and **where it looks is not a single fixed path**. Since FOG 1.6.1 +over TFTP, and **where it looks is not a single fixed path**. In FOG 1.6.0 this is true of *every* UEFI binary FOG ships, not just upstream's — none of them embed a script any more. iPXE asks for the bare name `autoexec.ipxe` and tries two locations in order: