+static ImageInfo *vmdk_get_extent_info(VmdkExtent *extent)
+{
+ ImageInfo *info = g_new0(ImageInfo, 1);
+
+ *info = (ImageInfo){
+ .filename = g_strdup(extent->file->filename),
+ .format = g_strdup(extent->type),
+ .virtual_size = extent->sectors * BDRV_SECTOR_SIZE,
+ .compressed = extent->compressed,
+ .has_compressed = extent->compressed,
+ .cluster_size = extent->cluster_sectors * BDRV_SECTOR_SIZE,
+ .has_cluster_size = !extent->flat,
+ };
+
+ return info;
+}
+
+static ImageInfoSpecific *vmdk_get_specific_info(BlockDriverState *bs)
+{
+ int i;
+ BDRVVmdkState *s = bs->opaque;
+ ImageInfoSpecific *spec_info = g_new0(ImageInfoSpecific, 1);
+ ImageInfoList **next;
+
+ *spec_info = (ImageInfoSpecific){
+ .kind = IMAGE_INFO_SPECIFIC_KIND_VMDK,
+ {
+ .vmdk = g_new0(ImageInfoSpecificVmdk, 1),
+ },
+ };
+
+ *spec_info->vmdk = (ImageInfoSpecificVmdk) {
+ .create_type = g_strdup(s->create_type),
+ .cid = s->cid,
+ .parent_cid = s->parent_cid,
+ };
+
+ next = &spec_info->vmdk->extents;
+ for (i = 0; i < s->num_extents; i++) {
+ *next = g_new0(ImageInfoList, 1);
+ (*next)->value = vmdk_get_extent_info(&s->extents[i]);
+ (*next)->next = NULL;
+ next = &(*next)->next;
+ }
+
+ return spec_info;
+}
+