[ipxe-devel] [PATCH 1/1] [efi] avoid unaligned read in efi_devpath_end()

Heinrich Schuchardt xypron.glpk at gmx.de
Wed Mar 28 18:49:22 UTC 2018


The old coding resulted in a "data abort" when compiled with gcc 6.3 for
armhf and run on an Allwinner A20 SOC.

The unaligned access occured when path->Length was on an uneven address.

Signed-off-by: Heinrich Schuchardt <xypron.glpk at gmx.de>
---
 src/interface/efi/efi_utils.c | 7 +++++--
 1 file changed, 5 insertions(+), 2 deletions(-)

diff --git a/src/interface/efi/efi_utils.c b/src/interface/efi/efi_utils.c
index 4dc75414..dd59613b 100644
--- a/src/interface/efi/efi_utils.c
+++ b/src/interface/efi/efi_utils.c
@@ -39,12 +39,15 @@ FILE_LICENCE ( GPL2_OR_LATER );
  * @ret path_end	End of device path
  */
 EFI_DEVICE_PATH_PROTOCOL * efi_devpath_end ( EFI_DEVICE_PATH_PROTOCOL *path ) {
+	EFI_DEVICE_PATH_PROTOCOL path_c;
 
-	while ( path->Type != END_DEVICE_PATH_TYPE ) {
+	memcpy(&path_c, path, sizeof(EFI_DEVICE_PATH_PROTOCOL));
+	while ( path_c.Type != END_DEVICE_PATH_TYPE ) {
 		path = ( ( ( void * ) path ) +
 			 /* There's this amazing new-fangled thing known as
 			  * a UINT16, but who wants to use one of those? */
-			 ( ( path->Length[1] << 8 ) | path->Length[0] ) );
+			 ( ( path_c.Length[1] << 8 ) | path_c.Length[0] ) );
+		memcpy(&path_c, path, sizeof(EFI_DEVICE_PATH_PROTOCOL));
 	}
 
 	return path;
-- 
2.11.0




More information about the ipxe-devel mailing list