@@ -100,9 +100,7 @@ static void drive_info_del(DriveInfo *dinfo)
if (!dinfo) {
return;
}
- if (dinfo->opts) {
- qemu_opts_del(dinfo->opts);
- }
+ qemu_opts_del(dinfo->opts);
g_free(dinfo->serial);
g_free(dinfo);
}
@@ -285,7 +285,6 @@ static BlockBackend *blockdev_init(const char *file, QDict *bs_opts,
int on_read_error, on_write_error;
BlockBackend *blk;
BlockDriverState *bs;
- DriveInfo *dinfo;
ThrottleConfig cfg;
int snapshot = 0;
bool copy_on_read;
@@ -457,9 +456,6 @@ static BlockBackend *blockdev_init(const char *file, QDict *bs_opts,
bdrv_set_io_limits(bs, &cfg);
}
- dinfo = g_malloc0(sizeof(*dinfo));
- blk_set_legacy_dinfo(blk, dinfo);
-
if (!file || !*file) {
if (has_driver_specific_opts) {
file = NULL;
@@ -903,21 +899,19 @@ DriveInfo *drive_new(QemuOpts *all_opts, BlockInterfaceType block_default_type)
}
/* Set legacy DriveInfo fields */
- dinfo = blk_legacy_dinfo(blk);
+ dinfo = g_malloc0(sizeof(*dinfo));
dinfo->enable_auto_del = true;
dinfo->opts = all_opts;
-
dinfo->cyls = cyls;
dinfo->heads = heads;
dinfo->secs = secs;
dinfo->trans = translation;
-
dinfo->type = type;
dinfo->bus = bus_id;
dinfo->unit = unit_id;
dinfo->devaddr = devaddr;
-
dinfo->serial = g_strdup(serial);
+ blk_set_legacy_dinfo(blk, dinfo);
switch(type) {
case IF_IDE:
@@ -19,7 +19,9 @@ void blkconf_serial(BlockConf *conf, char **serial)
if (!*serial) {
/* try to fall back to value set with legacy -drive serial=... */
dinfo = blk_legacy_dinfo(conf->blk);
- *serial = g_strdup(dinfo->serial);
+ if (dinfo) {
+ *serial = g_strdup(dinfo->serial);
+ }
}
}
@@ -32,11 +34,13 @@ void blkconf_geometry(BlockConf *conf, int *ptrans,
if (!conf->cyls && !conf->heads && !conf->secs) {
/* try to fall back to value set with legacy -drive cyls=... */
dinfo = blk_legacy_dinfo(conf->blk);
- conf->cyls = dinfo->cyls;
- conf->heads = dinfo->heads;
- conf->secs = dinfo->secs;
- if (ptrans) {
- *ptrans = dinfo->trans;
+ if (dinfo) {
+ conf->cyls = dinfo->cyls;
+ conf->heads = dinfo->heads;
+ conf->secs = dinfo->secs;
+ if (ptrans) {
+ *ptrans = dinfo->trans;
+ }
}
}
if (!conf->cyls && !conf->heads && !conf->secs) {
@@ -206,7 +206,7 @@ static int ide_drive_initfn(IDEDevice *dev)
{
DriveInfo *dinfo = blk_legacy_dinfo(dev->conf.blk);
- return ide_dev_initfn(dev, dinfo->media_cd ? IDE_CD : IDE_HD);
+ return ide_dev_initfn(dev, dinfo && dinfo->media_cd ? IDE_CD : IDE_HD);
}
#define DEFINE_IDE_DEV_PROPERTIES() \
@@ -2331,7 +2331,7 @@ static void scsi_disk_realize(SCSIDevice *dev, Error **errp)
}
dinfo = blk_legacy_dinfo(dev->conf.blk);
- if (dinfo->media_cd) {
+ if (dinfo && dinfo->media_cd) {
scsi_cd_realize(dev, errp);
} else {
scsi_hd_realize(dev, errp);
blockdev_init() always creates a DriveInfo, but only drive_new() fills it in. qmp_blockdev_add() leaves it blank. This results in a drive with type = IF_IDE, bus = 0, unit = 0. Screwed up in commit ee13ed1c. Board initialization code looking for IDE drive (0,0) can pick up one of these bogus drives. Not sure whether getting the QMP command executed early enough is likely in practice, though. Fix by creating DriveInfo in drive_new(). Block backends created by blockdev-add don't get one. A few places assume a block backend always has a DriveInfo. Fix them up. Signed-off-by: Markus Armbruster <armbru@redhat.com> --- block/block-backend.c | 4 +--- blockdev.c | 10 ++-------- hw/block/block.c | 16 ++++++++++------ hw/ide/qdev.c | 2 +- hw/scsi/scsi-disk.c | 2 +- 5 files changed, 15 insertions(+), 19 deletions(-)