Skip to content

Platform/RaspberryPi: Fix RPI_FW_MAC_ADDR_TAG value buffer size - #1042

Open
valtzu wants to merge 1 commit into
tianocore:masterfrom
valtzu:rpifirmware-mac-addr-tag-padding
Open

Platform/RaspberryPi: Fix RPI_FW_MAC_ADDR_TAG value buffer size#1042
valtzu wants to merge 1 commit into
tianocore:masterfrom
valtzu:rpifirmware-mac-addr-tag-padding

Conversation

@valtzu

@valtzu valtzu commented Aug 30, 2026

Copy link
Copy Markdown
Contributor

Fix reading mac address on RPi4.

Background

2 years ago I submitted a bugfix for populating serial number on RPi4. That fix turned into larger refactoring. That refactoring caused another bug: #908.

I actually received an email from Oleg (sorry don't know his GH handle) reporting this same issue right after the changes were merged, but I didn't manage to look into it back then.

Interesting thing is that with older firmware (e.g. 1.20241125) there were no issues, so it seems that at some point the firmware started returning an error if you provide it with an unaligned block of memory (not 100% sure on this).

The mailbox property interface pads each tag's value buffer to a 32-bit
boundary so the following tags and the end tag stay aligned.

Commit 6170839 ("RPiFirmwareDxe: Fix and consolidate incorrect
pragma pack blocks") moved RPI_FW_MAC_ADDR_TAG under the module-wide
#pragma pack(1) block. Its "UINT32 Padding" member then no longer rounds
the struct up to a multiple of 4: the packed tag is 10 bytes (6-byte MAC
address + 4-byte Padding), which leaves the trailing end tag misaligned.
Recent VideoCore firmware rejects such a request with a 0x80000001
partial response, so RpiFirmwareGetMacAddress () fails and callers fall
back to an all-zero MAC address.

Replace the UINT32 with a 2-byte Padding array so the packed struct is
8 bytes - the smallest multiple of 4 that holds the 6-byte address.

Signed-off-by: valtzu <valtzu@gmail.com>
@ardbiesheuvel

Copy link
Copy Markdown
Member

Can we just get rid of the #pragma pack(1) entirely? Looking at #217, few of those types were packed to begin with before you changed this, and the only field that really needs packing is the serial number. E.g.,

--- a/Platform/RaspberryPi/Drivers/RpiFirmwareDxe/RpiFirmwareDxe.c
+++ b/Platform/RaspberryPi/Drivers/RpiFirmwareDxe/RpiFirmwareDxe.c
@@ -31,7 +31,6 @@
 //
 #define NUM_PAGES   1
 
-#pragma pack(1)
 typedef struct {
   UINT32    BufferSize;
   UINT32    Response;
@@ -69,7 +68,6 @@ typedef struct {
 
 typedef struct {
   UINT8                     MacAddress[6];
-  UINT32                    Padding;
 } RPI_FW_MAC_ADDR_TAG;
 
 typedef struct {
@@ -80,7 +78,7 @@ typedef struct {
 } RPI_FW_GET_MAC_ADDR_CMD;
 
 typedef struct {
-  UINT64                    Serial;
+  UINT32                    Serial[2];
 } RPI_FW_SERIAL_TAG;
 
 typedef struct {
@@ -254,7 +252,6 @@ typedef struct {
   RPI_FW_GPIO_SET_CFG_TAG      TagBody;
   UINT32                       EndTag;
 } RPI_FW_NOTIFY_GPIO_SET_CFG_CMD;
-#pragma pack()
 
 STATIC VOID  *mDmaBuffer;
 STATIC VOID  *mDmaBufferMapping;
@@ -549,7 +546,7 @@ RpiFirmwareGetSerial (
     return EFI_DEVICE_ERROR;
   }
 
-  *Serial = Cmd->TagBody.Serial;
+  CopyMem (Serial, Cmd->TagBody.Serial, sizeof (*Serial));
   ReleaseSpinLock (&mMailboxLock);
   // Some platforms return 0 or 0x0000000010000000 for serial.
   // For those, try to use the MAC address.

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.

2 participants