mirror of https://github.com/acidanthera/audk.git
ArmPkg/BdsLib: Prevent a hang in BdsConnectDevicePath() when a sub-device path is not found
Some device paths were making BdsConnectDevicePath() hang. To prevent these hangs we check if the handle returned by gBS->LocateDevicePath() is the same after each iteration. An example of a device path that hangs: PciRoot(0x0)/Pci(0x1,0x0)/USB(0x0,0x0)/USB(0x3,0x0)/HD(...) The connect controller function manages to find PciRoot()/Pci(0x1,0x0) but the USB driver does not produce USB(0x0,0x0)/USB(0x3,0x0) and returns EFI_SUCCESS on its initialization. Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Olivier Martin <olivier.martin@arm.com> git-svn-id: https://svn.code.sf.net/p/edk2/code/trunk/edk2@15835 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
parent
5e6322a530
commit
04ad241e20
|
@ -311,27 +311,40 @@ BdsConnectAndUpdateDevicePath (
|
|||
EFI_DEVICE_PATH* Remaining;
|
||||
EFI_DEVICE_PATH* NewDevicePath;
|
||||
EFI_STATUS Status;
|
||||
EFI_HANDLE PreviousHandle;
|
||||
|
||||
if ((DevicePath == NULL) || (*DevicePath == NULL) || (Handle == NULL)) {
|
||||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
PreviousHandle = NULL;
|
||||
do {
|
||||
Remaining = *DevicePath;
|
||||
|
||||
// The LocateDevicePath() function locates all devices on DevicePath that support Protocol and returns
|
||||
// the handle to the device that is closest to DevicePath. On output, the device path pointer is modified
|
||||
// to point to the remaining part of the device path
|
||||
Status = gBS->LocateDevicePath (&gEfiDevicePathProtocolGuid, &Remaining, Handle);
|
||||
|
||||
if (!EFI_ERROR (Status)) {
|
||||
// Recursive = FALSE: We do not want to start all the device tree
|
||||
Status = gBS->ConnectController (*Handle, NULL, Remaining, FALSE);
|
||||
if (*Handle == PreviousHandle) {
|
||||
//
|
||||
// If no forward progress is made try invoking the Dispatcher.
|
||||
// A new FV may have been added to the system and new drivers
|
||||
// may now be found.
|
||||
// Status == EFI_SUCCESS means a driver was dispatched
|
||||
// Status == EFI_NOT_FOUND means no new drivers were dispatched
|
||||
//
|
||||
Status = gDS->Dispatch ();
|
||||
}
|
||||
|
||||
/*// We need to check if RemainingDevicePath does not point on the last node. Otherwise, calling
|
||||
// NextDevicePathNode () will return an undetermined Device Path Node
|
||||
if (!IsDevicePathEnd (RemainingDevicePath)) {
|
||||
RemainingDevicePath = NextDevicePathNode (RemainingDevicePath);
|
||||
}*/
|
||||
if (!EFI_ERROR (Status)) {
|
||||
PreviousHandle = *Handle;
|
||||
|
||||
// Recursive = FALSE: We do not want to start the whole device tree
|
||||
Status = gBS->ConnectController (*Handle, NULL, Remaining, FALSE);
|
||||
}
|
||||
}
|
||||
} while (!EFI_ERROR (Status) && !IsDevicePathEnd (Remaining));
|
||||
|
||||
if (!EFI_ERROR (Status)) {
|
||||
|
|
|
@ -14,7 +14,6 @@
|
|||
|
||||
#include "BdsInternal.h"
|
||||
|
||||
#include <Library/DxeServicesTableLib.h>
|
||||
#include <Library/HobLib.h>
|
||||
#include <Library/TimerLib.h>
|
||||
#include <Library/PrintLib.h>
|
||||
|
|
|
@ -19,6 +19,7 @@
|
|||
#include <Library/ArmLib.h>
|
||||
#include <Library/BaseLib.h>
|
||||
#include <Library/BaseMemoryLib.h>
|
||||
#include <Library/DxeServicesTableLib.h>
|
||||
#include <Library/HobLib.h>
|
||||
#include <Library/UefiBootServicesTableLib.h>
|
||||
#include <Library/UefiLib.h>
|
||||
|
|
Loading…
Reference in New Issue