boot: Show the device path for EFI bootflows
If the bootflow relates to the EFI bootmeth, show the device path along with the other info. Signed-off-by: Simon Glass <sjg@chromium.org>
This commit is contained in:
@@ -13,6 +13,7 @@
|
||||
#include <command.h>
|
||||
#include <console.h>
|
||||
#include <dm.h>
|
||||
#include <efi_device_path.h>
|
||||
#include <expo.h>
|
||||
#include <log.h>
|
||||
#include <mapmem.h>
|
||||
@@ -453,6 +454,22 @@ static int do_bootflow_info(struct cmd_tbl *cmdtp, int flag, int argc,
|
||||
printf("FDT addr: %lx\n", bflow->fdt_addr);
|
||||
}
|
||||
printf("Error: %d\n", bflow->err);
|
||||
if (IS_ENABLED(CONFIG_BOOTMETH_EFI) &&
|
||||
bflow->method->driver == DM_DRIVER_GET(bootmeth_4efi)) {
|
||||
struct efi_device_path *dp;
|
||||
bool alloced;
|
||||
|
||||
ret = efi_dp_from_bootflow(bflow, &dp, &alloced);
|
||||
printf("EFI path ");
|
||||
if (!ret) {
|
||||
printf("%pD\n", dp);
|
||||
if (alloced)
|
||||
efi_free_pool(dp);
|
||||
} else {
|
||||
printf("(err %dE)\n", ret);
|
||||
}
|
||||
}
|
||||
|
||||
if (dump && bflow->buf) {
|
||||
/* Set some sort of maximum on the size */
|
||||
int size = min(bflow->size, 10 << 10);
|
||||
|
||||
@@ -23,6 +23,8 @@
|
||||
#include <net.h>
|
||||
#endif
|
||||
|
||||
struct udevice;
|
||||
|
||||
/* Type INTN in UEFI specification */
|
||||
#define efi_intn_t ssize_t
|
||||
/* Type UINTN in UEFI specification*/
|
||||
@@ -848,4 +850,17 @@ efi_status_t efi_run_image(void *source_buffer, efi_uintn_t source_size,
|
||||
struct efi_device_path *dp_dev,
|
||||
struct efi_device_path *dp_img);
|
||||
|
||||
/**
|
||||
* efi_dp_from_bootdev() - Get the device path from a bootdev
|
||||
*
|
||||
* This is only available in the app. It looks up the bootdev and returns the
|
||||
* assocated device path (attached to its sibling block device)
|
||||
*
|
||||
* @dev: UCLASS_BOOTDEV device to check
|
||||
* @dpp: Returns device path on success
|
||||
* Returns: 0 if OK, -ve on error
|
||||
*/
|
||||
int efi_dp_from_bootdev(const struct udevice *dev,
|
||||
const struct efi_device_path **dpp);
|
||||
|
||||
#endif /* _LINUX_EFI_H */
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
|
||||
enum uclass_id;
|
||||
struct blk_desc;
|
||||
struct bootflow;
|
||||
struct efi_load_option;
|
||||
struct udevice;
|
||||
|
||||
@@ -429,4 +430,17 @@ struct efi_device_path *efi_dp_from_http(const char *server,
|
||||
const char *efi_dp_guess_uclass(struct efi_device_path *device_path,
|
||||
enum uclass_id *guessp);
|
||||
|
||||
/**
|
||||
* efi_dp_from_bootflow() - Get the device path for a bootflow
|
||||
*
|
||||
* @bflow: Bootflow to check
|
||||
* @dpp: Returns the device path
|
||||
* @allocedp: if NULL, no allocation is permitted, otherwise retrusn true if
|
||||
* efi_free_pool() must be called to free the device path
|
||||
* Return: 0 if OK, -EINVAL if @allocedp is NULL and allocation is needed,
|
||||
* -ve on error
|
||||
*/
|
||||
int efi_dp_from_bootflow(const struct bootflow *bflow,
|
||||
struct efi_device_path **dpp, bool *allocedp);
|
||||
|
||||
#endif /* EFI_DEVICE_PATH_H */
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
#define LOG_CATEGORY LOGC_EFI
|
||||
|
||||
#include <blk.h>
|
||||
#include <bootflow.h>
|
||||
#include <dm.h>
|
||||
#include <dm/root.h>
|
||||
#include <efi_device_path.h>
|
||||
@@ -1376,3 +1377,39 @@ const char *efi_dp_guess_uclass(struct efi_device_path *device_path,
|
||||
return best_name;
|
||||
}
|
||||
|
||||
int efi_dp_from_bootflow(const struct bootflow *bflow,
|
||||
struct efi_device_path **dpp, bool *allocedp)
|
||||
{
|
||||
struct udevice *bdev = bflow->dev;
|
||||
struct blk_desc *desc;
|
||||
struct udevice *blk;
|
||||
int ret;
|
||||
|
||||
if (IS_ENABLED(CONFIG_EFI_APP)) {
|
||||
const struct efi_device_path *dpc;
|
||||
|
||||
ret = efi_dp_from_bootdev(bflow->dev, &dpc);
|
||||
if (ret)
|
||||
return log_msg_ret("dfa", ret);
|
||||
*dpp = (struct efi_device_path *)dpc;
|
||||
if (allocedp)
|
||||
*allocedp = false;
|
||||
} else {
|
||||
struct efi_device_path *dp;
|
||||
|
||||
if (!allocedp)
|
||||
return log_msg_ret("dfb", -EINVAL);
|
||||
ret = bootdev_get_sibling_blk(bdev, &blk);
|
||||
if (ret)
|
||||
return log_msg_ret("dfc", ret);
|
||||
|
||||
desc = dev_get_uclass_plat(blk);
|
||||
dp = efi_dp_from_part(desc, bflow->part);
|
||||
if (!dp)
|
||||
return log_msg_ret("dfd", -ENOMEM);
|
||||
*allocedp = true;
|
||||
*dpp = dp;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
*/
|
||||
|
||||
#include <bootm.h>
|
||||
#include <dm.h>
|
||||
#include <efi.h>
|
||||
#include <efi_api.h>
|
||||
#include <efi_device_path.h>
|
||||
@@ -89,3 +90,20 @@ efi_status_t efi_binary_run_dp(void *image, size_t size, void *fdt,
|
||||
{
|
||||
return efi_run_image(image, size, dp_dev, dp_img);
|
||||
}
|
||||
|
||||
int efi_dp_from_bootdev(const struct udevice *dev,
|
||||
const struct efi_device_path **dpp)
|
||||
{
|
||||
const struct udevice *media = dev_get_parent(dev);
|
||||
const struct efi_media_plat *plat;
|
||||
|
||||
log_debug("dev '%s': uclass ID %d\n", media->name,
|
||||
device_get_uclass_id(media));
|
||||
if (device_get_uclass_id(media) != UCLASS_EFI_MEDIA)
|
||||
return log_msg_ret("efb", -ENOTSUPP);
|
||||
|
||||
plat = dev_get_plat(media);
|
||||
*dpp = plat->device_path;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user