summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorAlexander Graf <agraf@suse.de>2016-04-11 14:16:18 (GMT)
committerTom Rini <trini@konsulko.com>2016-04-18 21:11:36 (GMT)
commit8c3df0bf2e530c6e6f592f5144ef4f456c9e0260 (patch)
tree0d412d7149894a05380224ac84ad07e2643c6d2f /lib
parent4a12a97c14217a5b02791040e464449f779fce43 (diff)
downloadu-boot-8c3df0bf2e530c6e6f592f5144ef4f456c9e0260.tar.xz
efi_loader: Add el torito support
When loading an el torito image, uEFI exposes said image as a raw block device to the payload. Let's do the same by creating new block devices with added offsets for the respective el torito partitions. Signed-off-by: Alexander Graf <agraf@suse.de>
Diffstat (limited to 'lib')
-rw-r--r--lib/efi_loader/efi_disk.c35
1 files changed, 35 insertions, 0 deletions
diff --git a/lib/efi_loader/efi_disk.c b/lib/efi_loader/efi_disk.c
index e30e728..b3d56a8 100644
--- a/lib/efi_loader/efi_disk.c
+++ b/lib/efi_loader/efi_disk.c
@@ -27,6 +27,8 @@ struct efi_disk_obj {
struct efi_block_io_media media;
/* EFI device path to this block device */
struct efi_device_path_file_path *dp;
+ /* Offset into disk for simple partitions */
+ lbaint_t offset;
};
static efi_status_t efi_disk_open_block(void *handle, efi_guid_t *protocol,
@@ -81,6 +83,7 @@ static efi_status_t EFIAPI efi_disk_rw_blocks(struct efi_block_io *this,
return EFI_EXIT(EFI_DEVICE_ERROR);
blksz = desc->blksz;
blocks = buffer_size / blksz;
+ lba += diskobj->offset;
#ifdef DEBUG_EFI
printf("EFI: %s:%d blocks=%x lba=%"PRIx64" blksz=%x dir=%d\n", __func__,
@@ -159,6 +162,7 @@ static void efi_disk_add_dev(char *name,
diskobj->ops = block_io_disk_template;
diskobj->ifname = cur_drvr->name;
diskobj->dev_index = dev_index;
+ diskobj->offset = offset;
/* Fill in EFI IO Media info (for read/write callbacks) */
diskobj->media.removable_media = desc->removable;
@@ -184,6 +188,31 @@ static void efi_disk_add_dev(char *name,
list_add_tail(&diskobj->parent.link, &efi_obj_list);
}
+static int efi_disk_create_eltorito(struct blk_desc *desc,
+ const struct block_drvr *cur_drvr,
+ int diskid)
+{
+ int disks = 0;
+#ifdef CONFIG_ISO_PARTITION
+ char devname[16] = { 0 }; /* dp->str is u16[16] long */
+ disk_partition_t info;
+ int part = 1;
+
+ if (desc->part_type != PART_TYPE_ISO)
+ return 0;
+
+ while (!part_get_info(desc, part, &info)) {
+ snprintf(devname, sizeof(devname), "%s%d:%d", cur_drvr->name,
+ diskid, part);
+ efi_disk_add_dev(devname, cur_drvr, desc, diskid, info.start);
+ part++;
+ disks++;
+ }
+#endif
+
+ return disks;
+}
+
/*
* U-Boot doesn't have a list of all online disk devices. So when running our
* EFI payload, we scan through all of the potentially available ones and
@@ -214,6 +243,12 @@ int efi_disk_register(void)
cur_drvr->name, i);
efi_disk_add_dev(devname, cur_drvr, desc, i, 0);
disks++;
+
+ /*
+ * El Torito images show up as block devices
+ * in an EFI world, so let's create them here
+ */
+ disks += efi_disk_create_eltorito(desc, cur_drvr, i);
}
}
printf("Found %d disks\n", disks);