diff options
-rw-r--r-- | lib/efi_loader/efi_disk.c | 54 |
1 files changed, 31 insertions, 23 deletions
diff --git a/lib/efi_loader/efi_disk.c b/lib/efi_loader/efi_disk.c index 4e78ade..c815711 100644 --- a/lib/efi_loader/efi_disk.c +++ b/lib/efi_loader/efi_disk.c @@ -28,11 +28,13 @@ struct efi_disk_obj { /* EFI Interface Media descriptor struct, referenced by ops */ struct efi_block_io_media media; /* EFI device path to this block device */ - struct efi_device_path_file_path *dp; + struct efi_device_path *dp; + /* partition # */ + unsigned int part; /* Offset into disk for simple partitions */ lbaint_t offset; /* Internal block device */ - const struct blk_desc *desc; + struct blk_desc *desc; }; static efi_status_t EFIAPI efi_disk_reset(struct efi_block_io *this, @@ -172,26 +174,26 @@ static const struct efi_block_io block_io_disk_template = { static void efi_disk_add_dev(const char *name, const char *if_typename, - const struct blk_desc *desc, + struct blk_desc *desc, int dev_index, - lbaint_t offset) + lbaint_t offset, + unsigned int part) { struct efi_disk_obj *diskobj; - struct efi_device_path_file_path *dp; - int objlen = sizeof(*diskobj) + (sizeof(*dp) * 2); /* Don't add empty devices */ if (!desc->lba) return; - diskobj = calloc(1, objlen); + diskobj = calloc(1, sizeof(*diskobj)); /* Fill in object data */ - dp = (void *)&diskobj[1]; + diskobj->dp = efi_dp_from_part(desc, part); + diskobj->part = part; diskobj->parent.protocols[0].guid = &efi_block_io_guid; diskobj->parent.protocols[0].protocol_interface = &diskobj->ops; diskobj->parent.protocols[1].guid = &efi_guid_device_path; - diskobj->parent.protocols[1].protocol_interface = dp; + diskobj->parent.protocols[1].protocol_interface = diskobj->dp; diskobj->parent.handle = diskobj; diskobj->ops = block_io_disk_template; diskobj->ifname = if_typename; @@ -207,17 +209,6 @@ static void efi_disk_add_dev(const char *name, diskobj->media.last_block = desc->lba - offset; diskobj->ops.media = &diskobj->media; - /* Fill in device path */ - diskobj->dp = dp; - dp[0].dp.type = DEVICE_PATH_TYPE_MEDIA_DEVICE; - dp[0].dp.sub_type = DEVICE_PATH_SUB_TYPE_FILE_PATH; - dp[0].dp.length = sizeof(*dp); - ascii2unicode(dp[0].str, name); - - dp[1].dp.type = DEVICE_PATH_TYPE_END; - dp[1].dp.sub_type = DEVICE_PATH_SUB_TYPE_END; - dp[1].dp.length = sizeof(*dp); - /* Hook up to the device list */ list_add_tail(&diskobj->parent.link, &efi_obj_list); } @@ -236,14 +227,18 @@ static int efi_disk_create_eltorito(struct blk_desc *desc, if (desc->part_type != PART_TYPE_ISO) return 0; + /* and devices for each partition: */ while (!part_get_info(desc, part, &info)) { snprintf(devname, sizeof(devname), "%s:%d", pdevname, part); efi_disk_add_dev(devname, if_typename, desc, diskid, - info.start); + info.start, part); part++; disks++; } + + /* ... and add block device: */ + efi_disk_add_dev(devname, if_typename, desc, diskid, 0, 0); #endif return disks; @@ -271,9 +266,22 @@ int efi_disk_register(void) uclass_next_device_check(&dev)) { struct blk_desc *desc = dev_get_uclass_platdata(dev); const char *if_typename = dev->driver->name; + disk_partition_t info; + int part = 1; printf("Scanning disk %s...\n", dev->name); - efi_disk_add_dev(dev->name, if_typename, desc, desc->devnum, 0); + + /* add devices for each partition: */ + while (!part_get_info(desc, part, &info)) { + efi_disk_add_dev(dev->name, if_typename, desc, + desc->devnum, 0, part); + part++; + } + + /* ... and add block device: */ + efi_disk_add_dev(dev->name, if_typename, desc, + desc->devnum, 0, 0); + disks++; /* @@ -309,7 +317,7 @@ int efi_disk_register(void) snprintf(devname, sizeof(devname), "%s%d", if_typename, i); - efi_disk_add_dev(devname, if_typename, desc, i, 0); + efi_disk_add_dev(devname, if_typename, desc, i, 0, 0); disks++; /* |