summaryrefslogtreecommitdiffstats
path: root/src/interface/efi/efi_local.c
diff options
context:
space:
mode:
authorMichael Brown2020-08-03 16:26:25 +0200
committerMichael Brown2020-08-03 16:41:30 +0200
commitc63e61df75c815da1dc93196bbb6a931743b736f (patch)
tree94ed0f9cf3d127dd1c1c0ca6bed5b539031996a4 /src/interface/efi/efi_local.c
parent[efi] Match EDK2 numbering for USB ports (diff)
downloadipxe-c63e61df75c815da1dc93196bbb6a931743b736f.tar.gz
ipxe-c63e61df75c815da1dc93196bbb6a931743b736f.tar.xz
ipxe-c63e61df75c815da1dc93196bbb6a931743b736f.zip
[efi] Use device path to locate filesystem from which we were loaded
The file:/ URI syntax may be used to refer to local files on the filesystem from which the iPXE binary was loaded. This is currently implemented by directly using the DeviceHandle recorded in our EFI_LOADED_IMAGE_PROTOCOL. This mechanism will fail when a USB-enabled build of iPXE is loaded from USB storage and subsequently installs its own USB host controller drivers, since doing so will disconnect and reconnect the existing USB storage drivers and thereby invalidate the original storage device handle. Fix by recording the device path for the loaded image's DeviceHandle at initialisation time and later using the recorded device path to locate the appropriate device handle. Signed-off-by: Michael Brown <mcb30@ipxe.org>
Diffstat (limited to 'src/interface/efi/efi_local.c')
-rw-r--r--src/interface/efi/efi_local.c15
1 files changed, 13 insertions, 2 deletions
diff --git a/src/interface/efi/efi_local.c b/src/interface/efi/efi_local.c
index bd010ad2..79ea822f 100644
--- a/src/interface/efi/efi_local.c
+++ b/src/interface/efi/efi_local.c
@@ -307,6 +307,7 @@ static int efi_local_open_volume ( struct efi_local *local,
EFI_GUID *protocol = &efi_simple_file_system_protocol_guid;
int ( * check ) ( struct efi_local *local, EFI_HANDLE device,
EFI_FILE_PROTOCOL *root, const char *volume );
+ EFI_DEVICE_PATH_PROTOCOL *path;
EFI_FILE_PROTOCOL *root;
EFI_HANDLE *handles;
EFI_HANDLE device;
@@ -328,8 +329,18 @@ static int efi_local_open_volume ( struct efi_local *local,
}
check = efi_local_check_volume_name;
} else {
- /* Use our loaded image's device handle */
- handles = &efi_loaded_image->DeviceHandle;
+ /* Locate filesystem from which we were loaded */
+ path = efi_loaded_image_path;
+ if ( ( efirc = bs->LocateDevicePath ( protocol, &path,
+ &device ) ) != 0 ) {
+ rc = -EEFI ( efirc );
+ DBGC ( local, "LOCAL %p could not locate file system "
+ "on %s: %s\n", local,
+ efi_devpath_text ( efi_loaded_image_path ),
+ strerror ( rc ) );
+ return rc;
+ }
+ handles = &device;
num_handles = 1;
check = NULL;
}