WIP: Feature/smb pxe dhcp static - #2
Merged
Merged
Conversation
Add optional disk mount with TOML extras reloading, SMB server wrapper, PXE/TFTP boot server, static DHCP reservations and per-MAC images. Update README/spec docs and gitignore build artifacts. Remove prebuilt gokrazy-router binaries from index.
Add unit tests for config ExpandEnv, LoadExtras, ApplyExtras and DHCP SetReservations/SetPXEOptions. Also cover MAC normalization.
…sers - Add UsePortableServer config + startPortable/startSamba split - Fix isSamba never set true in startSamba (broke AddUser) - Hoist extras scope in main, apply extras.SMBUsers after SMB start - Add SMB unit tests (template, AddUser guard, New) - Move hostapd ctrl_interface /var/run -> /tmp (gokrazy compat) - MkdirAll ctrl dir before hostapd launch
Document PXE (TFTP) and HTTP boot server design, per-VLAN netboot configuration, DHCP PXE option injection for legacy/iPXE/UEFI clients, and static IP reservation + per-client netboot image selection via the MAC mapping file.
Document where each configuration file is placed on the router (/etc/gokrazy-router.json, macmap TOML, /data/netboot/). Add netboot/ directory with example router config, MAC map, iPXE script, and pxelinux config.
Remove accidentally committed ELF binaries (gokrazy-router, gokrazy-router-status). Update .gitignore to cover all build artifacts. Add cross-compile examples for ARMv7 and amd64 to README. Both architectures build cleanly.
Cherry-picked 4 commits from feature/netboot: - a4529b6 - Add netboot service and MAC-to-IP mapping to spec and README - 3c233c2 - Add config file location docs and netboot example configs - 472faf9 - Remove binaries, document amd64 build support - 1d79863 - Add amd64 to CI build matrix Rename CLI gokrazy-router-status -> router-cli (not grcli). Bug fix: isSamba flag, extras SMBUsers application, hostapd ctrl path
Add 'router-cli extras' subcommand to manage DHCP reservations and PXE boot image mappings stored in the extras TOML file on SMB share. - ExtrasConfig: Add Encode/Save/SetReservation/RemoveReservation/ SetMacImage/RemoveMacImage methods + ErrNotModified sentinel - CLI: Refactor to subcommand pattern (status, extras) - CLI extras: list, set-reservation, remove-reservation, set-mac-image, remove-mac-image with --file path - Tests: 6 new tests for extras CRUD and save/load round-trip
7 tests covering list, set-reservation, remove-reservation, set-mac-image, remove-mac-image, and bad-arg handling.
Move DHCP option 67 bootfile and PXE default image into the disk-based extras TOML. ApplyExtras now propagates these to all VLAN/WiFi DHCP configs and PXE config.
… scoped reservations - Add /api/reload to re-apply extras (reservations, PXE images, SMB users) without reboot - Support per-MAC DHCP option 67 bootfiles for legacy/UEFI PXE - Replace pin/tftp with a minimal SO_BINDTODEVICE-aware TFTP server for VLAN PXE - Scope DHCP reservations per subnet so VLAN entries do not leak across servers - Add VLAN address overrides in extras file
…er-class - Add per-MAC override, legacy/UEFI/iPXE bootfiles - Use DHCP option 77 (User Class) to detect iPXE and serve boot.ipxe - Use DHCP option 93 (Client System Architecture) for legacy vs UEFI - Defaults: undionly.kpxe (legacy), netboot.xyz.efi (UEFI), boot.ipxe (iPXE)
Differentiate clients by DHCP option 77 (iPXE) and option 93 (UEFI). Add netboot.xyz chain script and runtime extras example. Update README/spec to current services.pxe config.
…e detection iPXE/UEFI detection previously overrode per-MAC option 67 bootfiles, so a client configured with its own bootfile (e.g. netboot.xyz.kpxe) got the generic ipxe/uefi/legacy default at the iPXE stage. Resolve bootfile in order: MAC override > iPXE > UEFI > legacy.
The DefaultImage fallback redirected every TFTP RRQ to the default binary (e.g. undionly.kpxe), so an iPXE text script requested as boot.ipxe was served as the iPXE binary (72159 bytes), chainloading a second iPXE instance. Plain filenames are now served literally; the default image applies only to MAC-named requests (01-xx-xx-xx-xx-xx) without a mapping. Also drop noisy TFTP ACK debug logging.
- boot.ipxe chains to the local netboot.xyz.ipxe via tftp://${next-server}
with an iPXE shell fallback instead of loading a kernel directly
- netboot.xyz.ipxe uses boot.netboot.xyz/menu.ipxe; the old
ipxe/netboot.xyz.ipxe path returns 404. HTTP is tried first because the
legacy undionly.kpxe build lacks HTTPS support
- router-extras.toml reflects the deployed T410i setup (undionly.kpxe
defaults, boot.ipxe as iPXE script, static reservation for the T410i)
- loadOrCreateExtras: create minimal extras from JSON config when file missing, at startup and on /api/reload (dedupes reload handler) - dhcp: iPXE user-class precedence above per-MAC bootfile; only T410i (legacy MAC) gets the iPXE chain, all others default to UEFI netboot.xyz.efi - docs: router-extras.toml key table, PXE boot-file precedence and a multi-interface example (VLAN 1/20/31 + WiFi reservations, per-MAC images, SMB users) - docs: fix dead netboot.xyz chain URL (menu.ipxe), HTTP-first script; deployment fetches undionly.kpxe to match shipped extras
TFTP requests could read arbitrary router files via .. traversal, absolute paths or escaping symlinks. Serve strictly inside the TFTP root and validate every resolved image path (macImages/defaultImage included) against it. Each transfer now runs on a dedicated ephemeral UDP socket (RFC 1350 transfer ID) with ACKs validated against the full client IP:port, isolating concurrent transfers from the same or relayed clients. Reload fixes: - ApplyExtras replaces PXE overrides instead of merging, so values removed from the extras TOML disappear at runtime (incl. clearing defaultImage) - SetDefaultImage and SetMacPXEBootFiles apply unconditionally - handler maps guarded by RWMutex; reload no longer races transfer goroutines Do not auto-bind the TFTP socket to the last VLAN bridge; an unbound listener serves every scope that advertises option 66/67. Align docs with iPXE-first boot-file precedence; add jail, transfer, duplicate-RRQ, reload-race and precedence-table tests. go mod tidy drops the unused pin/tftp dependency.
…ning Reload (/api/reload) no longer mutates live network state: it is serialized under a mutex, and changes that cannot be applied at runtime ([vlanAddresses], [[smbUsers]]) are rejected with HTTP 409 instead of being half-applied. The admin API now binds to 127.0.0.1:8080 by default and requires a Bearer token for POST /api/reload unless allowUnauthenticatedReload is set. SMB extras users are now granted share access: ValidUsers is rendered from primary + extras users before Samba starts, and smbpasswd runs for each user; portable mode rejects extras. TFTP jail uses openat/O_NOFOLLOW per path component to close the TOCTOU symlink-swap gap, and the final DATA block is now ACKed with bounded retransmit. DHCP pool exhaustion returns nil allocation instead of duplicating a reserved/leased address.
Add global dns field to Config struct as fallback for DHCP scopes. Add DNS to ExtrasConfig for runtime override via router-extras.toml. Apply global DNS to VLAN, WiFi, LAN scopes that lack per-scope config. New files: - netboot/download-boot-files.sh: idempotent boot binary download Updated templates: - gokrazy-router.json: add DNS, VLAN 31, updated paths - router-extras.toml: add DNS entry, MAC reservation - macmap.toml: example entry placeholder
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Add portable SMB server option, fix SMB bugs, hostapd ctrl path fix
SMB: portable-smb-server support
usePortableServerconfig flag selects fiddyschmitt/portable-smb-server instead of SambasmbdStart()dispatches tostartPortable()orstartSamba()based on config or binary nameAddUser()method for extras-driven additional SMB users (Samba mode only)SMB: bug fixes
isSambanever set —startSamba()didn't sets.isSamba = true, causingAddUser()to always fail with "only supported in Samba mode"extras.SMBUsersnot applied — TOML extras file parsed[[smbUsers]]but the list was never used. Now hoistedextrasvar scope and iterated after SMB startcreateUserrefactored — usesSMB_CONF_PATHenv var instead of derivingsmbpasswdpath fromsmbdbin dir; simplified add/update logicSMB: unit tests
interfacesparam, custom share names)AddUserguard rejects portable modeNewconstructor baseline checkHostapd ctrl path
ctrl_interfacefrom/var/run/hostapdto/tmp/hostapd—/var/runmay not be writable in gokrazy's minimal rootfsMkdirAllbefore hostapd launch to ensure directory exists