pftf/RPi4

Set NETWORK_HTTP_BOOT_ENABLE for HTTP boot

andreiw opened this issue ยท 18 comments

NetworkPkg/TlsDxe also didn't build. Samer will have a pull request.

HTTP boot works with IPv4 and IPv6. Patch sent to EDK2

10155350
10155436

rgl commented

Can it also boot from https?

Can it also boot from https?

Yup.

20205046
20205059

One interesting challenge for HTTPS Boot testing was to create the Server certs in supported format.

I ran into an issue with the IPv4 literal certificate being rejected during the TLS verification. This BZ https://bugzilla.tianocore.org/show_bug.cgi?id=960 had a good and documented answer. The instructions at https://github.com/tianocore/tianocore.github.io/wiki/HTTP-Boot are outdated, and need to be updated.

rgl commented

Thanks for the explanation and links, really appreciate them!

Does this also support some kind of secure boot? Like secure dhcp/dns to protect against rogue servers in the network?

There is TLS verification, where you enroll the HTTP server certificate in the the UEFI client (in this case, the RPi). You can do this from the "Tls Auth Configuration" menu under "Device Manager" in UEFI Setup (see picture below). These "TLS certs" will get saved in a special UEFI non-volatile database.

The HTTPs Boot client (The RPi UEFI firmware) will then authenticate the server it is booting from using enrolled certificates before performing HTTPs Boot.

Note that this has nothing to do with "UEFI Secure Boot", which can be enabled independently, and verifies the image loaded from the disk or network (whether it is PXE, HTTP Boot, or HTTPs Boot) against certs/signatures in the UEFI Secure Boot databases.

Also note that in the EDK2 patch (tianocore/edk2-platforms@3daa701) I also enabled PcdAllowHttpConnections PCD. This allows booting from HTTP (no TLS) as well as HTTPs URLs.

10155439

rgl commented

Now I have to try it! :-)

If I use the binaries from https://ci.appveyor.com/project/pbatard/RPi4/build/artifacts I will get this change?

Can all of this firmware be stored inside the rpi 4 eeprom like the rpi bootloader? Or I always need to have an sd-card with these files inside?

Is there a way to automatically configure the CA certificates, etc? Like, putting the configuration inside a file? or calling an API to set it? or as the configuration seems to be stored in nvram, is there a tool to manipulate it and just drop it somewhere?

Thank You!

The releases are to be found on https://github.com/pftf/RPi4/releases. Please do not use the AppVeyor artifacts unless you know what you're doing, because you may end up with non-working builds.

Can all of this firmware be stored inside the rpi 4 eeprom like the rpi bootloader?

No. The RPi4 eeprom is way too small for that. Maybe that will change in the future, but for the time being, you need to use an SD card always.

Just extract all the files from the latest release zip file onto an SD card formatted as FAT16/FAT32 and you should be good to go.

Also be mindful that, because we have not yet added a driver for the internal network adapter (Genet), if your plan is to boot from the default network interface, that will not work with the current firmware.

Please be very mindful that the firmware is still not ready for production and many elements that you might expect to work by default do not work yet.

rgl commented

I've read all the disclaimers, and since this cannot brick the pi its cool ;-)

Also, do you have any idea about my other question about how to automatically configure the emulated nvram?

That's not a bad question. Once you configure it you can just copy the RPI_EFI.FD around (for other boards). To automatically configure you would need some human-readable marshalling formatted file that could be automatically sucked in once on first boot if NVRAM contents are invalid.

The way to do this is using the UEFI variable:

GUID: 0xfd2340D0, 0x3dab, 0x4349, { 0xa6, 0xc7, 0x3b, 0x4f, 0x12, 0xb4, 0x8e, 0xae } 
Name: "TlsCaCertificate"

This variable is defined in https://github.com/tianocore/edk2/blob/master/NetworkPkg/Include/Guid/TlsAuthentication.h

The variable is formatted as an EFI_SIGNATURE_LIST.

To read/write the variable, look at the code in EnrollX509toVariable() in https://github.com/tianocore/edk2/blob/master/NetworkPkg/TlsAuthConfigDxe/TlsAuthConfigImpl.c

One could write a UEFI Shell utility that can do this

rgl commented

Oh my two usb 3 gigabit ethernet network dongles (based on the AX88179 and r8152 chip) do not work with this because they do not appear on the Device Manager Devices List :-(

From what I understood the only chips supported are the ones at https://github.com/tianocore/edk2-platforms/tree/master/Drivers/OptionRomPkg/Bus/Usb/UsbNetworking, which have the Ax88772(b) chip, is that correct?

The GENET (onboard NIC) is not supported yet, but is getting very close. Also, there are USB drivers for ASIX and Realtek devices that you can load manually (or rebuild the FW to include the binary). Try this for the Ax88179: https://www.asix.com.tw/FrootAttach/driver/AX88179_178A_UEFI_V2.8.0_ARM_AARCH64.zip

I also have source code for the Ax88179. I will make it available on a branch later today. eventually, it will be up-streamed to EDK2 under UsbNetworking. I also have a Realtek UEFI driver that I can share if you want to try it.

rgl commented

Nice to known about GENET is getting close to being cooked, that will make things much easier :-)

Also having the Ax88179 code up-streamed would be nice! :-)

I didn't realized that I could just go to the vendor and get their blobs! So, I've placed .efi files at the root of the disk, but the network card is still not in the Device List. I have to manually load the .efi somehow? Sorry for asking so many newbie questions, but I known pretty much nothing about UEFI and I'm trying to learn more about it by using it on the pi ;-)

Placing the EFI driver on the filesystem does not cause it to load. You need to manually do this from the Shell using:

Load <EFiDriverName.efi>
Connect -r

After this, you will see the network drivers bind to the newly loaded driver. You can verify this from the Shell using the command:

drivers
Look for the driver handle of your specific driver that was loaded. To view details of what got installed on that driver image (including controllers it manages, and any children) do:

dh -d -v <DriverHandle>

Of course there are other ways to get the driver (from the filesystem) to automatically get loaded during boot (by adding it to the DriverOrder), or even rebuild the full RPI FW image to include the .EFI binary in it. But the Shell method above is straightforward

rgl commented

For reference, I described how I "shoe-horned/automated" my usb 3.0 to ethernet dongle to do dhcp at:

https://gist.github.com/rgl/95b8ccd6b3453f548907b579d4d04a72

Many thanks for your input!