Skip to content

GbE-region MAC randomisation - #2171

Open
FckBigTch wants to merge 4 commits into
linuxboot:masterfrom
Nitrokey:mac_randomisation
Open

GbE-region MAC randomisation#2171
FckBigTch wants to merge 4 commits into
linuxboot:masterfrom
Nitrokey:mac_randomisation

Conversation

@FckBigTch

@FckBigTch FckBigTch commented Jul 29, 2026

Copy link
Copy Markdown

Follow-up to the PoC in #1195. This PR builds on that work and it is a feature to view and randomize the Ethernet MAC address stored in the GbE region of the flash.

Module

  • Add nvmutil (from the Libreboot project).

Makefile

  • Add ifdtool (from coreboot) as a build target in the Makefile, built directly from the board's coreboot checkout with Heads' existing cross toolchain to coreboot's own module configure step.

initrd/bin/gui-init.sh

  • Add a "MAC address randomization" submenu in gui-init.sh, gated on boards config CONFIG_NVMUTIL=y and CONFIG_IFDTOOL=y.

initrd/etc/functions.sh

  • Add show_mac
  • Add change_mac
  • Add clean_up_mac, remove temporary files

initrd/bin/flash.sh

  • Adjust CONFIG_FLASH_OPTIONS depending on which function invoked flash.sh

board/

  • Add CONFIG_FLASH_TOOL="flashprog --progress --programmer internal"
  • Change CONFIG_FLASH_OPTIONS to CONFIG_FLASH_OPTIONS="${CONFIG_FLASH_TOOL} --ifd -i bios -i me -i fd"

GUI

New submenu under the main menu, shown only when both CONFIG_NVMUTIL and CONFIG_IFDTOOL are set to yes for the board:

  • Show current Ethernet MAC address
  • Randomize Ethernet MAC address (fully random)
  • Randomize Ethernet MAC address using a valid OUI (locally-administered/universal OUI pattern, so the result still looks like a plausible vendor-assigned address)
menu mac_menu

Tested boards

@tlaurion tlaurion left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for picking up on #1195 !

There is ways to make menu options dynamic, thinking of unlocking spi per boot per config settings as an example. Will look deeper in further code review

Comment thread modules/nvmutil Outdated
@tlaurion

tlaurion commented Jul 29, 2026

Copy link
Copy Markdown
Collaborator

Confused on how ifdtool is built here vs #1195 (which was unclean still, required coreboot's built ifdtool that is needed to build coreboot (see modules/coreboot there) to add Makefile hacks to pack ifdtool as cbmem is packed to be used inside of Heads.

ifdtool needs to be built with musl-cross-make to depend on musl's libc; so unclear how building it with coreboot's buildstack produces an actual working ifdtool to be used inside of heads? You tested this pr @FckBigTch ?

@FckBigTch

Copy link
Copy Markdown
Author

Confused on how ifdtool is built here vs #1195 (which was unclean still, required coreboot's built ifdtool that is needed to build coreboot (see modules/coreboot there) to add Makefile hacks to pack ifdtool as cbmem is packed to be used inside of Heads.

ifdtool needs to be built with musl-cross-make to depend on musl's libc; so unclear how building it with coreboot's buildstack produces an actual working ifdtool to be used inside of heads? You tested this pr @FckBigTch ?

Yes, I've tested several times, and flashed the resulting ROMs on t480s, t480 and x230. Ifdtool is usable inside of heads.
I just tried to do it like cbmem, superiotool or inteltool.
ifdtool is built from '$(build)/$(coreboot_dir)/util/ifdtool' using the board's own coreboot source tree, musl-cross-make and the board's DOTCONFIG, rather than duplicating the source tree.

Confirmed it's actually musl:

file build/x86/coreboot-25.09/util/ifdtool/ifdtool
build/x86/coreboot-25.09/util/ifdtool/ifdtool: ELF 64-bit LSB executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib/ld-musl-x86_64.so.1, with debug_info, not stripped

Interpreter is /lib/ld-musl-x86_64.so.1

@tlaurion

tlaurion commented Aug 1, 2026

Copy link
Copy Markdown
Collaborator

Some notes from deeper review

  • why we say it doesn't work with v540tu/v560tu? from a point of view of board config (flash command) v540tu/v560tu do the right thing here: they exclude for future internal flash the GBE region by specifying flash regions that are intended to be flashed only (desired, otherwise an internal upgrade would replace GBE with hardcoded mac) : export CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal --ifd -i bios -i me -i fd"
    • Actually, by merging this PR, all boards that can have their mac address changed should have that flash command changed to exclude GBE from flashing from internal upgrades, otherwise replacing it in internal flashing of new rom ( right now : export CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal" so overwriting the whole flash )
    • What is missing in this PR is now a distinction for overriding temporarily (at runtime only) of the GBE region when flashing that section only with flashtool export from board config so changing GBE would only be done explicitly when the user wants to override its mac from config menu options, no? export CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal --ifd -i bios -i me -i fd -i gbe"
  • Still missing: dynamic menu option.
  • Interesting gain here with ifdtool packed in, we could (other PR, not here) extract MRC cache and inject it in the rom so that memory training happens only if not matching (flashing rom with current commands overwirte the memory training cache, resulting in long boot times after flash for all DDR4, DDR5 taking up to near a minute before raminit is finished, which is the part drawing bootsplash on screen, leaving user in the dark up to that point.)

Will think about that a bit more. If you have ideas let me know @FckBigTch

@FckBigTch

Copy link
Copy Markdown
Author

Some notes from deeper review

* why we say it doesn't work with v540tu/v560tu? from a point of view of board config (flash command) v540tu/v560tu do the right thing here: they exclude for future internal flash the GBE region by specifying flash regions that are intended to be flashed only (desired, otherwise an internal upgrade would replace GBE with hardcoded mac) :  `export CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal --ifd -i bios -i me -i fd"`
  
  * Actually, by merging this PR, all boards that can have their mac address changed should have that flash command changed to exclude GBE from flashing from internal upgrades, otherwise replacing it in internal flashing of new rom ( right now : `export CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal"` so overwriting the whole flash )
  * What is missing in this PR is now a distinction for overriding temporarily (at runtime only) of the GBE region when flashing that section only with flashtool export from board config so changing GBE would only be done explicitly when the user wants to override its mac from config menu options, no? `export CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal --ifd -i bios -i me -i fd -i gbe"`

* Still missing: dynamic menu option.

* Interesting gain here with ifdtool packed in, we could (other PR, not here) extract MRC cache and inject it in the rom so that memory training happens only if not matching (flashing rom with current commands overwirte the memory training cache, resulting in long boot times after flash for all DDR4, DDR5 taking up to near a minute before raminit is finished, which is the part drawing bootsplash on screen, leaving user in the dark up to that point.)

Will think about that a bit more. If you have ideas let me know @FckBigTch

The reason I thought the Novacustom models should be excluded is that the config explicitly states:
"NovaCustom V54 MTL (integrated graphics) board configuration
Note the FLASH_OPTIONS: '--ifd -i bios -i me -i fd'
This excludes gbe from internal flashing, otherwise mac address would revert to '88:88:88:88:87:88' see #1871 (comment)
Same options should be used when externally flashing the first time, otherwise Intel GbE region (Ethernet config blob) will be overwritten and MAC reverted to '88:88:88:88:87:88'.”

That means it's not possible to generate a random MAC address, right? But I understand that overwriting the GBE region should be avoided during an update.

I hadn't even thought of the idea with the dynamic menu. I'll follow your advice and try to implement it.

@tlaurion

tlaurion commented Aug 2, 2026

Copy link
Copy Markdown
Collaborator

The reason I thought the Novacustom models should be excluded is that the config explicitly states:
"NovaCustom V54 MTL (integrated graphics) board configuration
Note the FLASH_OPTIONS: '--ifd -i bios -i me -i fd'
This excludes gbe from internal flashing, otherwise mac address would revert to '88:88:88:88:87:88' see #1871 (comment)
Same options should be used when externally flashing the first time, otherwise Intel GbE region (Ethernet config blob) will be overwritten and MAC reverted to '88:88:88:88:87:88'.”

That means it's not possible to generate a random MAC address, right? But I understand that overwriting the GBE region should be avoided during an update.

Misunderstanding. This means those boards pack a GBE (see coreboot configs) but don't ever flash it per initial flashing instructions or internal flashing. If someone misread initial flashing (which is done by OEM not end users in the case of these boards), then MAC address would become generic as per packed in rom GBE.

I hadn't even thought of the idea with the dynamic menu. I'll follow your advice and try to implement it.

@tlaurion

tlaurion commented Aug 2, 2026

Copy link
Copy Markdown
Collaborator

The reason I thought the Novacustom models should be excluded is that the config explicitly states:
"NovaCustom V54 MTL (integrated graphics) board configuration
Note the FLASH_OPTIONS: '--ifd -i bios -i me -i fd'
This excludes gbe from internal flashing, otherwise mac address would revert to '88:88:88:88:87:88' see #1871 (comment)
Same options should be used when externally flashing the first time, otherwise Intel GbE region (Ethernet config blob) will be overwritten and MAC reverted to '88:88:88:88:87:88'.”

That means it's not possible to generate a random MAC address, right? But I understand that overwriting the GBE region should be avoided during an update.

Misunderstanding. This means those boards pack a GBE (see coreboot configs) but don't ever flash it per initial flashing instructions or internal flashing. If someone misread initial flashing (which is done by OEM not end users in the case of these boards), then MAC address would become generic as per packed in rom GBE.

Also see linuxboot/heads-wiki#209 (needed)

@FckBigTch
FckBigTch force-pushed the mac_randomisation branch 3 times, most recently from fc5e070 to 03a9a5a Compare August 4, 2026 12:49
@FckBigTch

Copy link
Copy Markdown
Author

I've revised the menu now. Instead of duplicating the whole function for the gated/non-gated case, the menu items are now built into a bash array, with the MAC randomization entry conditionally appended only when CONFIG_NVMUTIL=y and CONFIG_IFDTOOL=y.

@tlaurion

tlaurion commented Aug 4, 2026

Copy link
Copy Markdown
Collaborator

Took a little time to think about linuxboot/heads-wiki#209 and current widespread

  • CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal"

It seems that the proper usage pattern would become, in all boards having GBE

  • CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal --ifd -i bios -i me -i fd" as v540tu/v560tu
  • And then, when calling flash.sh for GBE persistence when MAC randomized, save current CONFIG_FLASH_OPTION to BACKUP_FLASH_OPTION (BACKUP_FLASH_OPTION=CONFIG_FLASH_OPTION), append GBE region for current flash op (CONFIG_FLASH_OPTION+=" -i gbe"), flash, and then restore CONFIG_FLASH_OPTION=BACKUP_FLASH_OPTION).

Thoughts @FckBigTch ?

@tlaurion

tlaurion commented Aug 4, 2026

Copy link
Copy Markdown
Collaborator

The reason I thought the Novacustom models should be excluded is that the config explicitly states:
"NovaCustom V54 MTL (integrated graphics) board configuration
Note the FLASH_OPTIONS: '--ifd -i bios -i me -i fd'
This excludes gbe from internal flashing, otherwise mac address would revert to '88:88:88:88:87:88' see #1871 (comment)
Same options should be used when externally flashing the first time, otherwise Intel GbE region (Ethernet config blob) will be overwritten and MAC reverted to '88:88:88:88:87:88'.”
That means it's not possible to generate a random MAC address, right? But I understand that overwriting the GBE region should be avoided during an update.

Misunderstanding. This means those boards pack a GBE (see coreboot configs) but don't ever flash it per initial flashing instructions or internal flashing. If someone misread initial flashing (which is done by OEM not end users in the case of these boards), then MAC address would become generic as per packed in rom GBE.

I hadn't even thought of the idea with the dynamic menu. I'll follow your advice and try to implement it.

Sorry i misled you @FckBigTch

grep -Ri gbe config/coreboot-* | grep nova
config/coreboot-novacustom-v540tu.config:CONFIG_MAINBOARD_USES_IFD_GBE_REGION=y
config/coreboot-novacustom-v540tu.config:# CONFIG_HAVE_GBE_BIN is not set
config/coreboot-novacustom-v560tu.config:CONFIG_MAINBOARD_USES_IFD_GBE_REGION=y
config/coreboot-novacustom-v560tu.config:# CONFIG_HAVE_GBE_BIN is not set

So, what that means is that the SPI chip HAS a GBE, but shipped ROM images don't and keep OEM's.
So. with IFDTOOL, we can get OEM unique GBE, modify it, flash it back.
The old "maximized" builds mindset was to put all required blobs (including config ones), where novacustom's took a different direction, which is arguably good but changed philosiphy as pointed in old heads-wiki doc so that initial flashing, and internal flashing, do not touch the region. Prior attempts to not pack GBE under x230 resulted in GBE not working correctly (we were overwritting GBE region by flashing whole SPI without one!), as well as current m900 workstation community effort not having working Ethernet, which i didn't investigate yet: but the m900 flashes with a backed GBE which for unknown reasons don't work.

So TLDR: We should have all boards having GBE only write to specific IFD's regions, not touching GBE even if one is provided by rom (excluding GBE from flashprog). And have GBE flashed when user intends it (when one is generated from nvmutil in this PR), where internal upgrade don't touch it unless expressively asked for. Makes sense?

Outside of v540tu/v560tu not having GBE in packed ROM; Others have it:

user@debian-13:~/heads-clean2$ grep -Ri "CONFIG_HAVE_GBE_BIN=y" config/coreboot-* | grep "\.config:"
config/coreboot-m900-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-optiplex-7019_9010-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-optiplex-7019_9010_TXT-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t420.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t420-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t430-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t440p.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t480-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t480s-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t520-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t530-dgpu-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t530-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-w530-dgpu-K1000m-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-w530-dgpu-K2000m-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-w530-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-w541.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-x220.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-x220-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-x230-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-x230-maximized-fhd_edp.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-z220-cmt.config:CONFIG_HAVE_GBE_BIN=y

Makes sense?

@FckBigTch

FckBigTch commented Aug 8, 2026

Copy link
Copy Markdown
Author

Took a little time to think about linuxboot/heads-wiki#209 and current widespread

* `CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal"`

It seems that the proper usage pattern would become, in all boards having GBE

* `CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal --ifd -i bios -i me -i fd"` as v540tu/v560tu

* And then, when calling flash.sh for GBE persistence when MAC randomized, save current CONFIG_FLASH_OPTION to BACKUP_FLASH_OPTION  (BACKUP_FLASH_OPTION=CONFIG_FLASH_OPTION), append GBE region for current flash op (CONFIG_FLASH_OPTION+="  -i gbe"), flash, and then restore CONFIG_FLASH_OPTION=BACKUP_FLASH_OPTION).

Thoughts @FckBigTch ?

I'm sorry for the late reply, but I had to think about what you wrote.
I’m still confused, not sure understanding you correctly.
Makes sense to me, defaulting all GBE-capable boards to exclude GBE from normal flash/update operations.
What I do not understand, why do you want to backup CONFIG_FLASH_OPTIONS?
You’re not just talking about MAC-randomization, but about flashing the gbe in general during an update or reflash?

If the user or whoever first did the (external) flash overwrote the GBE, so it’s DE:AD:CO:FF:EE. If they use the randomization feature, they get a random MAC. If all boards exclude GBE (CONFIG_FLASH_OPTIONS change), the random mac is persistent during an update.
Do you want to give the user the option to have the GBE overwritten again during an update or reflash so that they get DE:AD:CO:FF:EE back?

I'm not sure if that's really necessary, but I understand that you want to offer an easy way to revert to the default settings.

@FckBigTch

Copy link
Copy Markdown
Author

The reason I thought the Novacustom models should be excluded is that the config explicitly states:
"NovaCustom V54 MTL (integrated graphics) board configuration
Note the FLASH_OPTIONS: '--ifd -i bios -i me -i fd'
This excludes gbe from internal flashing, otherwise mac address would revert to '88:88:88:88:87:88' see #1871 (comment)
Same options should be used when externally flashing the first time, otherwise Intel GbE region (Ethernet config blob) will be overwritten and MAC reverted to '88:88:88:88:87:88'.”
That means it's not possible to generate a random MAC address, right? But I understand that overwriting the GBE region should be avoided during an update.

Misunderstanding. This means those boards pack a GBE (see coreboot configs) but don't ever flash it per initial flashing instructions or internal flashing. If someone misread initial flashing (which is done by OEM not end users in the case of these boards), then MAC address would become generic as per packed in rom GBE.

I hadn't even thought of the idea with the dynamic menu. I'll follow your advice and try to implement it.

Sorry i misled you @FckBigTch

grep -Ri gbe config/coreboot-* | grep nova
config/coreboot-novacustom-v540tu.config:CONFIG_MAINBOARD_USES_IFD_GBE_REGION=y
config/coreboot-novacustom-v540tu.config:# CONFIG_HAVE_GBE_BIN is not set
config/coreboot-novacustom-v560tu.config:CONFIG_MAINBOARD_USES_IFD_GBE_REGION=y
config/coreboot-novacustom-v560tu.config:# CONFIG_HAVE_GBE_BIN is not set

So, what that means is that the SPI chip HAS a GBE, but shipped ROM images don't and keep OEM's. So. with IFDTOOL, we can get OEM unique GBE, modify it, flash it back. The old "maximized" builds mindset was to put all required blobs (including config ones), where novacustom's took a different direction, which is arguably good but changed philosiphy as pointed in old heads-wiki doc so that initial flashing, and internal flashing, do not touch the region. Prior attempts to not pack GBE under x230 resulted in GBE not working correctly (we were overwritting GBE region by flashing whole SPI without one!), as well as current m900 workstation community effort not having working Ethernet, which i didn't investigate yet: but the m900 flashes with a backed GBE which for unknown reasons don't work.

So TLDR: We should have all boards having GBE only write to specific IFD's regions, not touching GBE even if one is provided by rom (excluding GBE from flashprog). And have GBE flashed when user intends it (when one is generated from nvmutil in this PR), where internal upgrade don't touch it unless expressively asked for. Makes sense?

Outside of v540tu/v560tu not having GBE in packed ROM; Others have it:

user@debian-13:~/heads-clean2$ grep -Ri "CONFIG_HAVE_GBE_BIN=y" config/coreboot-* | grep "\.config:"
config/coreboot-m900-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-optiplex-7019_9010-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-optiplex-7019_9010_TXT-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t420.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t420-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t430-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t440p.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t480-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t480s-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t520-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t530-dgpu-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-t530-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-w530-dgpu-K1000m-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-w530-dgpu-K2000m-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-w530-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-w541.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-x220.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-x220-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-x230-maximized.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-x230-maximized-fhd_edp.config:CONFIG_HAVE_GBE_BIN=y
config/coreboot-z220-cmt.config:CONFIG_HAVE_GBE_BIN=y

Makes sense?

So, is there anything else you'd like me to do?
I can make the changes to CONFIG_FLASH_OPTIONS for all relevant boards like this
CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal --ifd -i bios -i me -i fd

@tlaurion

tlaurion commented Aug 8, 2026

Copy link
Copy Markdown
Collaborator

Took a little time to think about linuxboot/heads-wiki#209 and current widespread

* `CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal"`

It seems that the proper usage pattern would become, in all boards having GBE

* `CONFIG_FLASH_OPTIONS="flashprog --progress --programmer internal --ifd -i bios -i me -i fd"` as v540tu/v560tu

* And then, when calling flash.sh for GBE persistence when MAC randomized, save current CONFIG_FLASH_OPTION to BACKUP_FLASH_OPTION  (BACKUP_FLASH_OPTION=CONFIG_FLASH_OPTION), append GBE region for current flash op (CONFIG_FLASH_OPTION+="  -i gbe"), flash, and then restore CONFIG_FLASH_OPTION=BACKUP_FLASH_OPTION).

Thoughts @FckBigTch ?

I'm sorry for the late reply, but I had to think about what you wrote. I’m still confused, not sure understanding you correctly. Makes sense to me, defaulting all GBE-capable boards to exclude GBE from normal flash/update operations. What I do not understand, why do you want to backup CONFIG_FLASH_OPTIONS? You’re not just talking about MAC-randomization, but about flashing the gbe in general during an update or reflash?

If the user or whoever first did the (external) flash overwrote the GBE, so it’s DE:AD:CO:FF:EE. If they use the randomization feature, they get a random MAC. If all boards exclude GBE (CONFIG_FLASH_OPTIONS change), the random mac is persistent during an update. Do you want to give the user the option to have the GBE overwritten again during an update or reflash so that they get DE:AD:CO:FF:EE back?

I'm not sure if that's really necessary, but I understand that you want to offer an easy way to revert to the default settings.

Sorry for having confused you. I checked the changes, and now I understand why the misunderstandings.
Everywhere in codebase, flashing operations use flash.sh wrapper which in turn uses CONFIG_FLASH_OPTIONS; you call flashprog directly. This is not a good pattern since if/when flashrom will have proper --progress support to inform use of progress of flashing operations, we might switch back to flashrom and calling the packed programmer directly is not what the codebase do without verifying its existence. flash.sh and CONFIG_FLASH_OPTIONS are used everywhere in codebase for that reason.

Once this is CONFIG_FLASH_OPTIONS and flash.sh used, why I wanted to keep prior CONFIG_FLASH_OPTIONS to restore it before returning to prior operations is exposed, otherwise a reboot.sh would be needed (also normal pattern after a flash. We might need to simply add in all boards CONFIG_FLASH_TOOL="flashprog" and CONFIG_FLASH_OPTIONS=$CONFIG_FLASH_TOOL --programmer....." so that you could use CONFIG_FLASH directly if that is the path you prefer without needing backup of previous board, extract the programmer to call only --ifd -i gbe... That's where I was going to.

gui-init.sh should not have additional functions, it should either be in functions.sh or gui_functions.sh that gui-init.sh sources. One cannot cd into /tmp in one function and not change back to prior location either since other heads workflows will break, unless a reboot is done too there. Some of your added functions do not check for ifdtool or nvutil presence (not guarded) which might also cause issues down the line which we try to not have to deal with.

Sorry I wasn't clear enough; I didn't see you were calling flashprog directly in added functions under gui-init.sh

@FckBigTch

Copy link
Copy Markdown
Author

Make sense! Thanks for your patience and explanations. I will make the changes.

@FckBigTch

Copy link
Copy Markdown
Author

I've made the changes. I set the t420 and x220 to "no" in the Tools section of the config because of the space issue (7 MB). I'm not sure if the new CONFIG_FLASH_OPTIONS still make sense for these boards. Maybe it would be better to stick with the old version without options after all?

Comment thread initrd/etc/functions.sh Outdated
Comment thread boards/EOL_t480s-hotp-maximized/EOL_t480s-hotp-maximized.config Outdated
@tlaurion

Copy link
Copy Markdown
Collaborator

I've made the changes. I set the t420 and x220 to "no" in the Tools section of the config because of the space issue (7 MB). I'm not sure if the new CONFIG_FLASH_OPTIONS still make sense for these boards. Maybe it would be better to stick with the old version without options after all?

yes, it should be unified everywhere (all boards) so we can clearly say in heads-wiki that we did a philosophical stance change; the user is left with a choice, per our discussions here, to flash externally with or without board's rom GBE, or, to keep the one that was fused in config per OEM/ODM. If we do so, the same general guidelines will be possible for all boards under https://osresearch.net/Flashing-guides (and we will be able to get rid of all those different flashing instructions which are basically duplicates with a generic "FLASHTOOL --progress --programmer XYZ [--chip ZYX] --ifd -i bios -i me -i fd" where user is invited to check for external programmer choice quirks without having to repeat ourselves.

Makes sense?

Comment thread initrd/bin/flash.sh

@tlaurion tlaurion left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I really think we need to distinguish/reuse FLASHTOOL/FLASH_OPTIONS to only flash gbe when needed, not touching anything else.

@tlaurion
tlaurion requested a balanced review from Copilot August 19, 2026 19:53
@tlaurion

tlaurion commented Sep 7, 2026

Copy link
Copy Markdown
Collaborator

@FckBigTch I asked for testing/comments under matrix channel

Please update OP to fit content. Ideally add screenshots :)

@tlaurion

tlaurion commented Sep 7, 2026

Copy link
Copy Markdown
Collaborator

Kano was merged. If you beat me to add, adding the same sperarion of flash prog and flash options to all boards would be necessary before merge.

- nvmutil from libreboot added as a module
- ifdtool from coreboot is included as a part of the Makefile

Signed-off-by: Rene <chaotic@disroot.org>
- Ethernet MAC address randomization - menu option is displayed only if $CONFIG_NVMUTIL=y and $CONFIG_IFDTOOL=y are set in the config file
- add mac_randomization_options_menu() - to select a completely random mac, an intel pattern or to show the current mac

Signed-off-by: Rene <chaotic@disroot.org>
@tlaurion

tlaurion commented Sep 7, 2026

Copy link
Copy Markdown
Collaborator

@FckBigTch I asked for testing/comments under matrix channel

Please update OP to fit content. Ideally add screenshots :)

Have you checked the matrix thread?

@Thrilleratplay

Copy link
Copy Markdown
Contributor

Tested on a W530. LGTM

@tlaurion

tlaurion commented Sep 8, 2026

Copy link
Copy Markdown
Collaborator

There is no reason waiting longer. Let's keep an eye open on bug reports and have that merged. Asking copilot for review one last time

@tlaurion
tlaurion requested review from tlaurion and a balanced review from Copilot September 8, 2026 00:18

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Changes recommended

Unhandled nvmutil failures, unsafe globally administered random addresses, and unsupported Kano enablement must be corrected.

Once you've addressed the issues Copilot identified, you can request another Copilot review.

Review details
  • Files reviewed: 40/42 changed files
  • Comments generated: 5
  • Review effort level: Balanced

Comment thread boards/kano-hotp/kano-hotp.config Outdated
Comment thread boards/kano/kano.config Outdated
Comment thread initrd/etc/functions.sh Outdated
Comment thread initrd/etc/functions.sh
Comment thread initrd/etc/functions.sh Outdated

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Changes recommended

Duplicate nvm invocations still mutate or read the GbE image before the checked calls, and the current-MAC dialog is shown before validating that a MAC was parsed.

Once you've addressed the issues Copilot identified, you can request another Copilot review.

Review details
  • Files reviewed: 40/42 changed files
  • Comments generated: 0 new
  • Review effort level: Balanced

@tlaurion

tlaurion commented Sep 8, 2026

Copy link
Copy Markdown
Collaborator

LGTM let's see if copilot has something relevant for final review

- add show_mac
- add change_mac
- add clean_up_mac, remove temporary files
- adjust CONFIG_FLASH_OPTIONS in flash.sh, for mac randomization

Signed-off-by: Rene <chaotic@disroot.org>
- add $CONFIG_NVMUTIL
- add $CONFIG_IFDTOOL
- change $CONFIG_FLASH_OPTIONS to "flashprog --progress --programmer internal --ifd -i bios -i me -i fd" for all boards have GBE packed in ROM
- t420 and x220, tools are set to no, does not fit in 7mb image (like dropbear)

Signed-off-by: Rene <chaotic@disroot.org>
@FckBigTch

Copy link
Copy Markdown
Author

I got my hopes up too soon, careless mistake. Now it should be fine

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🔵 Needs a closer look

It changes firmware-region extraction and flashing across many hardware targets, including numerous boards not listed as tested.

Review details
  • Files reviewed: 40/42 changed files
  • Comments generated: 0 new
  • Review effort level: Balanced

@tlaurion

tlaurion commented Sep 9, 2026

Copy link
Copy Markdown
Collaborator

@FckBigTch Hmm, retested on v540tu and to be flashed mac was the old one when selecting intel random one

debug_redacted.log

See

DEBUG: whiptail_type: type=normal args=--title Ethernet MAC randomization --menu Select An Option 0 80 10 r Generate a fully randomized ethernet MAC address i Use a intel based universal pattern (OUI) to generate a random ethernet MAC address s Show the current ethernet MAC address m <-- Return to main menu
DEBUG: whiptail_type: whiptail --title Ethernet MAC randomization --menu Select An Option 0 80 10 r Generate a fully randomized ethernet MAC address i Use a intel based universal pattern (OUI) to generate a random ethernet MAC address s Show the current ethernet MAC address m <-- Return to main menu
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3719)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3676)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:9)
DEBUG: Flash options detected: flashprog --progress --programmer internal --ifd -i bios -i me -i fd
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:17) -> INFO(/etc/functions.sh:297)
INFO: Board novacustom-v540tu detected with flash options configured
DEBUG: flash.sh: called from show_mac()
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3709) -> whiptail_type(/etc/gui_functions.sh:112)
DEBUG: whiptail_type: type=normal args=--title Show current MAC address --msgbox Current MAC address: 88:88:88:88:87:88 0 80
DEBUG: whiptail_type: whiptail --title Show current MAC address --msgbox Current MAC address: 88:88:88:88:87:88 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3769) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --msgbox New, modified ethernet MAC address to be flashed: 88:88:88:88:87:88 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3772) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --yesno Do you really want to change the ethernet MAC address?\n\nNote: generated addresses claim Intel's globally administered address space and can collide with a legitimately assigned Intel device. 0 80 --no-button Do not change --yes-button Change
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3787) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Canceled --msgbox Ethernet MAC address change canceled. 0 80

Specifically

DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --msgbox New, modified ethernet MAC address to be flashed: 88:88:88:88:87:88 0 80

I would recommend adding more DO_WITH_DEBUG and DEBUG calls to sink output to /tmp/debug.log.

Will try to debug further later on, but it seems that the old mac is used instead of new one, probably variables reusal where new ones should be used after https://github.com/linuxboot/heads/compare/ffdb947542e263bad9d0da2c673db84543bb4ddf..050e5b8d17be5d6d7439ac949ecb0f6d7ae892fc

@tlaurion

tlaurion commented Sep 9, 2026

Copy link
Copy Markdown
Collaborator

@FckBigTch Hmm, retested on v540tu and to be flashed mac was the old one when selecting intel random one

debug_redacted.log

See

DEBUG: whiptail_type: type=normal args=--title Ethernet MAC randomization --menu Select An Option 0 80 10 r Generate a fully randomized ethernet MAC address i Use a intel based universal pattern (OUI) to generate a random ethernet MAC address s Show the current ethernet MAC address m <-- Return to main menu
DEBUG: whiptail_type: whiptail --title Ethernet MAC randomization --menu Select An Option 0 80 10 r Generate a fully randomized ethernet MAC address i Use a intel based universal pattern (OUI) to generate a random ethernet MAC address s Show the current ethernet MAC address m <-- Return to main menu
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3719)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3676)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:9)
DEBUG: Flash options detected: flashprog --progress --programmer internal --ifd -i bios -i me -i fd
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:17) -> INFO(/etc/functions.sh:297)
INFO: Board novacustom-v540tu detected with flash options configured
DEBUG: flash.sh: called from show_mac()
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3709) -> whiptail_type(/etc/gui_functions.sh:112)
DEBUG: whiptail_type: type=normal args=--title Show current MAC address --msgbox Current MAC address: 88:88:88:88:87:88 0 80
DEBUG: whiptail_type: whiptail --title Show current MAC address --msgbox Current MAC address: 88:88:88:88:87:88 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3769) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --msgbox New, modified ethernet MAC address to be flashed: 88:88:88:88:87:88 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3772) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --yesno Do you really want to change the ethernet MAC address?\n\nNote: generated addresses claim Intel's globally administered address space and can collide with a legitimately assigned Intel device. 0 80 --no-button Do not change --yes-button Change
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3787) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Canceled --msgbox Ethernet MAC address change canceled. 0 80

Specifically

DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --msgbox New, modified ethernet MAC address to be flashed: 88:88:88:88:87:88 0 80

I would recommend adding more DO_WITH_DEBUG and DEBUG calls to sink output to /tmp/debug.log.

Will try to debug further later on, but it seems that the old mac is used instead of new one, probably variables reusal where new ones should be used after https://github.com/linuxboot/heads/compare/ffdb947542e263bad9d0da2c673db84543bb4ddf..050e5b8d17be5d6d7439ac949ecb0f6d7ae892fc

Actually, my bad completely; I had previously written over gbe region with null content over past upgrades manually. So borrowed my v560tu gbe region, injected it in v540tu full backup rom, flashed back and generated intel mac twice and worked flawlessly.

debug.log

But this testing makes me wonder if we could speed things up just reading --ifd -i gbe, writing directy into it with nvm and flashing it back without ifdtool altogether. Will try. Still want ifdtool though for next iterations.

@FckBigTch

Copy link
Copy Markdown
Author

@FckBigTch Hmm, retested on v540tu and to be flashed mac was the old one when selecting intel random one
debug_redacted.log
See

DEBUG: whiptail_type: type=normal args=--title Ethernet MAC randomization --menu Select An Option 0 80 10 r Generate a fully randomized ethernet MAC address i Use a intel based universal pattern (OUI) to generate a random ethernet MAC address s Show the current ethernet MAC address m <-- Return to main menu
DEBUG: whiptail_type: whiptail --title Ethernet MAC randomization --menu Select An Option 0 80 10 r Generate a fully randomized ethernet MAC address i Use a intel based universal pattern (OUI) to generate a random ethernet MAC address s Show the current ethernet MAC address m <-- Return to main menu
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3719)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3676)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:9)
DEBUG: Flash options detected: flashprog --progress --programmer internal --ifd -i bios -i me -i fd
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:17) -> INFO(/etc/functions.sh:297)
INFO: Board novacustom-v540tu detected with flash options configured
DEBUG: flash.sh: called from show_mac()
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3709) -> whiptail_type(/etc/gui_functions.sh:112)
DEBUG: whiptail_type: type=normal args=--title Show current MAC address --msgbox Current MAC address: 88:88:88:88:87:88 0 80
DEBUG: whiptail_type: whiptail --title Show current MAC address --msgbox Current MAC address: 88:88:88:88:87:88 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3769) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --msgbox New, modified ethernet MAC address to be flashed: 88:88:88:88:87:88 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3772) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --yesno Do you really want to change the ethernet MAC address?\n\nNote: generated addresses claim Intel's globally administered address space and can collide with a legitimately assigned Intel device. 0 80 --no-button Do not change --yes-button Change
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3787) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Canceled --msgbox Ethernet MAC address change canceled. 0 80

Specifically

DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --msgbox New, modified ethernet MAC address to be flashed: 88:88:88:88:87:88 0 80

I would recommend adding more DO_WITH_DEBUG and DEBUG calls to sink output to /tmp/debug.log.
Will try to debug further later on, but it seems that the old mac is used instead of new one, probably variables reusal where new ones should be used after https://github.com/linuxboot/heads/compare/ffdb947542e263bad9d0da2c673db84543bb4ddf..050e5b8d17be5d6d7439ac949ecb0f6d7ae892fc

Actually, my bad completely; I had previously written over gbe region with null content over past upgrades manually. So borrowed my v560tu gbe region, injected it in v540tu full backup rom, flashed back and generated intel mac twice and worked flawlessly.

Phew, I thought here comes the next problem.

debug.log

But this testing makes me wonder if we could speed things up just reading --ifd -i gbe, writing directy into it with nvm and flashing it back without ifdtool altogether. Will try. Still want ifdtool though for next iterations.

That sounds interesting. I'll be away for the next two days, but I'll check it out after that.

@tlaurion

tlaurion commented Sep 9, 2026

Copy link
Copy Markdown
Collaborator

@FckBigTch Hmm, retested on v540tu and to be flashed mac was the old one when selecting intel random one
debug_redacted.log
See

DEBUG: whiptail_type: type=normal args=--title Ethernet MAC randomization --menu Select An Option 0 80 10 r Generate a fully randomized ethernet MAC address i Use a intel based universal pattern (OUI) to generate a random ethernet MAC address s Show the current ethernet MAC address m <-- Return to main menu
DEBUG: whiptail_type: whiptail --title Ethernet MAC randomization --menu Select An Option 0 80 10 r Generate a fully randomized ethernet MAC address i Use a intel based universal pattern (OUI) to generate a random ethernet MAC address s Show the current ethernet MAC address m <-- Return to main menu
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3719)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3676)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:9)
DEBUG: Flash options detected: flashprog --progress --programmer internal --ifd -i bios -i me -i fd
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:17) -> INFO(/etc/functions.sh:297)
INFO: Board novacustom-v540tu detected with flash options configured
DEBUG: flash.sh: called from show_mac()
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3709) -> whiptail_type(/etc/gui_functions.sh:112)
DEBUG: whiptail_type: type=normal args=--title Show current MAC address --msgbox Current MAC address: 88:88:88:88:87:88 0 80
DEBUG: whiptail_type: whiptail --title Show current MAC address --msgbox Current MAC address: 88:88:88:88:87:88 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3769) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --msgbox New, modified ethernet MAC address to be flashed: 88:88:88:88:87:88 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3772) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --yesno Do you really want to change the ethernet MAC address?\n\nNote: generated addresses claim Intel's globally administered address space and can collide with a legitimately assigned Intel device. 0 80 --no-button Do not change --yes-button Change
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3787) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Canceled --msgbox Ethernet MAC address change canceled. 0 80

Specifically

DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --msgbox New, modified ethernet MAC address to be flashed: 88:88:88:88:87:88 0 80

I would recommend adding more DO_WITH_DEBUG and DEBUG calls to sink output to /tmp/debug.log.
Will try to debug further later on, but it seems that the old mac is used instead of new one, probably variables reusal where new ones should be used after https://github.com/linuxboot/heads/compare/ffdb947542e263bad9d0da2c673db84543bb4ddf..050e5b8d17be5d6d7439ac949ecb0f6d7ae892fc

Actually, my bad completely; I had previously written over gbe region with null content over past upgrades manually. So borrowed my v560tu gbe region, injected it in v540tu full backup rom, flashed back and generated intel mac twice and worked flawlessly.

debug.log

But this testing makes me wonder if we could speed things up just reading --ifd -i gbe, writing directy into it with nvm and flashing it back without ifdtool altogether. Will try. Still want ifdtool though for next iterations.

user@debian-13:~/heads-gbe_rando$ git diff Nitrokey/mac_randomisation 
diff --git a/initrd/bin/flash.sh b/initrd/bin/flash.sh
index 047f4106494..10bac8f4f4a 100755
--- a/initrd/bin/flash.sh
+++ b/initrd/bin/flash.sh
@@ -35,9 +35,9 @@ case "$CHANGE_FLASH_OPTIONS" in
   gbe_only )
   DEBUG "flash.sh: called from mac_randomization(), adding gbe"
     # --noverify-all: only verify the included (gbe) region, not the whole
-    # 32MB SPI, after writing. See flashprog(8): automatic verification after
-    # -w reads out the whole chip unless not-included regions are skipped.
-    CONFIG_FLASH_OPTIONS="${CONFIG_FLASH_TOOL} --ifd --image gbe --noverify-all"
+    # 32MB SPI (no bios), after writing. See flashprog(8): automatic verification after
+    # -w/-r reads out the whole chip unless not-included regions are skipped.
+    CONFIG_FLASH_OPTIONS="${CONFIG_FLASH_TOOL} --ifd --image fd --image gbe --noverify-all"
   ;;
   * )
     : # no change
diff --git a/initrd/etc/functions.sh b/initrd/etc/functions.sh
index a786a411efe..8af553da2b7 100644
--- a/initrd/etc/functions.sh
+++ b/initrd/etc/functions.sh
@@ -3678,7 +3678,7 @@ show_mac(){
        if [ "$CONFIG_IFDTOOL" = "y" ]; then
 
                # read whole SPI-chip and save it to /tmp/$CONFIG_BOARD.rom
-               CHANGE_FLASH_OPTIONS=whole_spi /bin/flash.sh -r /tmp/${CONFIG_BOARD}.rom
+               CHANGE_FLASH_OPTIONS=gbe_only /bin/flash.sh -r /tmp/${CONFIG_BOARD}.rom
 
                # test if file is > 0 byte
                if [ ! -s /tmp/${CONFIG_BOARD}.rom ]; then
@@ -3793,7 +3793,10 @@ change_mac() {
                clean_up_mac
        fi
 
+       #Clean /tmp artififacts
        clean_up_mac
+       #We overriden flash options: reboot.
+       reboot.sh
 }
 
 clean_up_mac(){

Really interesting gains since most of 32Mib chips is skipped, reading --ifd -i fb and -i gbe is all that is needed for iftool + nvm actions.

Problem with this path alone is that Heads complains not being able to succeed upon preserve_rom which is called unconditionally in code as of this pr for now:


> [...]
> TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:924) -> whiptail_type(/etc/gui_functions.sh:118) -> whiptail_error(/etc/gui_functions.sh:99)
DEBUG: whiptail_error: whiptail --background-gradient 0 0 0 150 0 0 --title Ethernet MAC randomization --menu Select An Option 0 80 10 r Generate a fully randomized ethernet MAC address i Use a intel based universal pattern (OUI) to generate a random ethernet MAC address s Show the current ethernet MAC address m  <-- Return to main menu
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3719)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3676)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:9)
DEBUG: Flash options detected: flashprog --progress --programmer internal --ifd -i bios -i me -i fd
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:17) -> INFO(/etc/functions.sh:297)
INFO: Board novacustom-v540tu detected with flash options configured
DEBUG: flash.sh: called from mac_randomization(), adding gbe
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3709) -> whiptail_type(/etc/gui_functions.sh:112)
DEBUG: whiptail_type: type=error args=--title Show current MAC address --msgbox Current MAC address: 00:1f:3b:1b:bf:3a 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3725) -> show_mac(/etc/functions.sh:3709) -> whiptail_type(/etc/gui_functions.sh:118) -> whiptail_error(/etc/gui_functions.sh:99)
DEBUG: whiptail_error: whiptail --background-gradient 0 0 0 150 0 0 --title Show current MAC address --msgbox Current MAC address: 00:1f:3b:1b:bf:3a 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3769) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --msgbox New, modified ethernet MAC address to be flashed: 00:1f:3b:0b:9b:25 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3772) -> whiptail_warning(/etc/gui_functions.sh:86)
DEBUG: whiptail_warning: whiptail --background-gradient 0 0 0 150 125 0 --title Change ethernet MAC --yesno Do you really want to change the ethernet MAC address?\n\nNote: generated addresses claim Intel's globally administered address space and can collide with a legitimately assigned Intel device. 0 80 --no-button Do not change --yes-button Change
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:9)
DEBUG: Flash options detected: flashprog --progress --programmer internal --ifd -i bios -i me -i fd
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:17) -> INFO(/etc/functions.sh:297)
INFO: Board novacustom-v540tu detected with flash options configured
DEBUG: flash.sh: called from mac_randomization(), adding gbe
 >> Preparing new ROM image for flashing
 >> Verifying SHA-256 checksum of ROM image
DEBUG: flash_rom: CLEAN=0 — preserving heads/ CBFS files
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:140) -> flash_rom(/bin/flash.sh:64) -> preserve_rom(/etc/functions.sh:480)
 >> Preserving configuration overrides and key material from current firmware: heads/initrd/.gnupg/pubring.kbx heads/initrd/.gnupg/trustdb.gpg heads/initrd/etc/config.user
DEBUG: preserve_rom: scanning /tmp/novacustom-v540tu.rom for existing heads/* entries to skip
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/cbfs.sh:0) -> main(/bin/cbfs.sh:6)
DEBUG: preserve_rom: heads/initrd/.gnupg/pubring.kbx not found in new ROM — copying from current CBFS
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/cbfs.sh:0) -> main(/bin/cbfs.sh:6)
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:140) -> flash_rom(/bin/flash.sh:64) -> preserve_rom(/etc/functions.sh:511) -> DIE(/etc/functions.sh:28)
!!! ERROR: preserve_rom: failed to write heads/initrd/.gnupg/pubring.kbx to /tmp/novacustom-v540tu.rom !!!
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/flash.sh:0) -> main(/bin/flash.sh:140) -> flash_rom(/bin/flash.sh:64) -> preserve_rom(/etc/functions.sh:511) -> DIE(/etc/functions.sh:44) -> INPUT(/etc/functions.sh:404)
INPUT: Press Enter to continue...
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3783) -> whiptail_error(/etc/gui_functions.sh:99)
DEBUG: whiptail_error: whiptail --background-gradient 0 0 0 150 0 0 --title Error --msgbox Flashing FAILED! 0 80
TRACE: main(/init:0) -> main(/bin/gui-init.sh:0) -> main(/bin/gui-init.sh:1069) -> show_main_menu(/bin/gui-init.sh:618) -> show_options_menu(/bin/gui-init.sh:684) -> mac_randomization_options_menu(/bin/gui-init.sh:938) -> change_mac(/etc/functions.sh:3784) -> recovery(/etc/functions.sh:1088)

Still investigating. Also restating that ifdtool will be really helpful in keeping MRC cache on dev cycles and to not scare users; a reminder that current flash.sh doesn't preserve it and results in black screen of around a minute each time a firmware update occurs(since there is no injection of current MRC cache into new rom to be flashed: causing it), this is reinforcing priority of #2138 (since next release will only contain code to deal with it, pushing fix to next flashing to preserve MRC cache across firmware upgrades).

@tlaurion

tlaurion commented Sep 9, 2026

Copy link
Copy Markdown
Collaborator

Cannot push directly to Nitrokey:mac_randomisation from this account (no collaborator write access — 403).

The same commits are pushed to tlaurion:mac_randomisation (my personal fork). If a Nitrokey maintainer can cherry-pick, or if someone with push access can run:

git fetch tlaurion mac_randomisation
git push Nitrokey tlaurion/mac_randomisation:mac_randomisation

the branch is ready to fast-forward into the PR.

Two commits, ahead of 050e5b8d17b:

  • d0217111flash: gate preserve_rom on whole-chip writes
  • 61ffcd59doc: synthesize flash concepts into one concise file

Both signed-off by Thierry Laurion. Verified on v540tu (novacustom-v540tu / novacustom-v560tu): the gbe_only path no longer errors on cbfs.sh -a for the BIOS-region-less temp image.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants