summary refs log tree commit diff stats
diff options
context:
space:
mode:
authorAnthony Liguori <aliguori@us.ibm.com>2011-11-28 11:15:10 -0600
committerAnthony Liguori <aliguori@us.ibm.com>2011-11-28 11:15:10 -0600
commit13bd0b5026265611809e99749bd74c2fd095247d (patch)
treefbc175b426cb2764b0c5362a72416d402cf95517
parentf04303743ac59361795b4f0effc3c01bea9b65a3 (diff)
parent5bb1cbac4fdb1ca28f33c8d68538d03e3db7c160 (diff)
downloadfocaccia-qemu-13bd0b5026265611809e99749bd74c2fd095247d.tar.gz
focaccia-qemu-13bd0b5026265611809e99749bd74c2fd095247d.zip
Merge remote-tracking branch 'kwolf/block-stable' into staging
-rw-r--r--block/qcow.c12
-rw-r--r--block/sheepdog.c2
-rw-r--r--block/vdi.c15
-rw-r--r--block/vmdk.c16
-rw-r--r--block/vpc.c18
-rw-r--r--block/vvfat.c17
-rw-r--r--hw/pci-hotplug.c3
-rw-r--r--hw/scsi-bus.c11
-rw-r--r--hw/scsi-generic.c5
-rw-r--r--hw/scsi.h2
-rw-r--r--hw/usb-msd.c4
-rw-r--r--hw/virtio-blk.c7
12 files changed, 99 insertions, 13 deletions
diff --git a/block/qcow.c b/block/qcow.c
index adecee06c9..4814ed0ced 100644
--- a/block/qcow.c
+++ b/block/qcow.c
@@ -26,6 +26,7 @@
 #include "module.h"
 #include <zlib.h>
 #include "aes.h"
+#include "migration.h"
 
 /**************************************************************/
 /* QEMU COW block driver with compression and encryption support */
@@ -74,6 +75,7 @@ typedef struct BDRVQcowState {
     AES_KEY aes_encrypt_key;
     AES_KEY aes_decrypt_key;
     CoMutex lock;
+    Error *migration_blocker;
 } BDRVQcowState;
 
 static int decompress_cluster(BlockDriverState *bs, uint64_t cluster_offset);
@@ -160,6 +162,12 @@ static int qcow_open(BlockDriverState *bs, int flags)
         bs->backing_file[len] = '\0';
     }
 
+    /* Disable migration when qcow images are used */
+    error_set(&s->migration_blocker,
+              QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED,
+              "qcow", bs->device_name, "live migration");
+    migrate_add_blocker(s->migration_blocker);
+
     qemu_co_mutex_init(&s->lock);
     return 0;
 
@@ -604,10 +612,14 @@ static int qcow_co_writev(BlockDriverState *bs, int64_t sector_num,
 static void qcow_close(BlockDriverState *bs)
 {
     BDRVQcowState *s = bs->opaque;
+
     g_free(s->l1_table);
     g_free(s->l2_cache);
     g_free(s->cluster_cache);
     g_free(s->cluster_data);
+
+    migrate_del_blocker(s->migration_blocker);
+    error_free(s->migration_blocker);
 }
 
 static int qcow_create(const char *filename, QEMUOptionParameter *options)
diff --git a/block/sheepdog.c b/block/sheepdog.c
index 9f8060960f..62f1f3a0cf 100644
--- a/block/sheepdog.c
+++ b/block/sheepdog.c
@@ -1116,6 +1116,7 @@ static int coroutine_fn add_aio_request(BDRVSheepdogState *s, AIOReq *aio_req,
     /* send a header */
     ret = do_write(s->fd, &hdr, sizeof(hdr));
     if (ret) {
+        qemu_co_mutex_unlock(&s->lock);
         error_report("failed to send a req, %s", strerror(errno));
         return -EIO;
     }
@@ -1123,6 +1124,7 @@ static int coroutine_fn add_aio_request(BDRVSheepdogState *s, AIOReq *aio_req,
     if (wlen) {
         ret = do_writev(s->fd, iov, wlen, aio_req->iov_offset);
         if (ret) {
+            qemu_co_mutex_unlock(&s->lock);
             error_report("failed to send a data, %s", strerror(errno));
             return -EIO;
         }
diff --git a/block/vdi.c b/block/vdi.c
index 684a4a87b6..02da6b44d0 100644
--- a/block/vdi.c
+++ b/block/vdi.c
@@ -52,6 +52,7 @@
 #include "qemu-common.h"
 #include "block_int.h"
 #include "module.h"
+#include "migration.h"
 
 #if defined(CONFIG_UUID)
 #include <uuid/uuid.h>
@@ -203,6 +204,8 @@ typedef struct {
     uint32_t bmap_sector;
     /* VDI header (converted to host endianness). */
     VdiHeader header;
+
+    Error *migration_blocker;
 } BDRVVdiState;
 
 /* Change UUID from little endian (IPRT = VirtualBox format) to big endian
@@ -454,6 +457,12 @@ static int vdi_open(BlockDriverState *bs, int flags)
         goto fail_free_bmap;
     }
 
+    /* Disable migration when vdi images are used */
+    error_set(&s->migration_blocker,
+              QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED,
+              "vdi", bs->device_name, "live migration");
+    migrate_add_blocker(s->migration_blocker);
+
     return 0;
 
  fail_free_bmap:
@@ -939,6 +948,12 @@ static int vdi_create(const char *filename, QEMUOptionParameter *options)
 
 static void vdi_close(BlockDriverState *bs)
 {
+    BDRVVdiState *s = bs->opaque;
+
+    g_free(s->bmap);
+
+    migrate_del_blocker(s->migration_blocker);
+    error_free(s->migration_blocker);
 }
 
 static coroutine_fn int vdi_co_flush(BlockDriverState *bs)
diff --git a/block/vmdk.c b/block/vmdk.c
index 96f7d5d90f..f5441591d7 100644
--- a/block/vmdk.c
+++ b/block/vmdk.c
@@ -26,6 +26,7 @@
 #include "qemu-common.h"
 #include "block_int.h"
 #include "module.h"
+#include "migration.h"
 #include <zlib.h>
 
 #define VMDK3_MAGIC (('C' << 24) | ('O' << 16) | ('W' << 8) | 'D')
@@ -97,6 +98,7 @@ typedef struct BDRVVmdkState {
     int num_extents;
     /* Extent array with num_extents entries, ascend ordered by address */
     VmdkExtent *extents;
+    Error *migration_blocker;
 } BDRVVmdkState;
 
 typedef struct VmdkMetaData {
@@ -659,7 +661,14 @@ static int vmdk_open(BlockDriverState *bs, int flags)
     }
     s->parent_cid = vmdk_read_cid(bs, 1);
     qemu_co_mutex_init(&s->lock);
-    return ret;
+
+    /* Disable migration when VMDK images are used */
+    error_set(&s->migration_blocker,
+              QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED,
+              "vmdk", bs->device_name, "live migration");
+    migrate_add_blocker(s->migration_blocker);
+
+    return 0;
 
 fail:
     vmdk_free_extents(bs);
@@ -1504,7 +1513,12 @@ exit:
 
 static void vmdk_close(BlockDriverState *bs)
 {
+    BDRVVmdkState *s = bs->opaque;
+
     vmdk_free_extents(bs);
+
+    migrate_del_blocker(s->migration_blocker);
+    error_free(s->migration_blocker);
 }
 
 static coroutine_fn int vmdk_co_flush(BlockDriverState *bs)
diff --git a/block/vpc.c b/block/vpc.c
index 39a324705d..89a5ee2668 100644
--- a/block/vpc.c
+++ b/block/vpc.c
@@ -25,6 +25,7 @@
 #include "qemu-common.h"
 #include "block_int.h"
 #include "module.h"
+#include "migration.h"
 
 /**************************************************************/
 
@@ -128,6 +129,8 @@ typedef struct BDRVVPCState {
 
     uint64_t last_bitmap;
 #endif
+
+    Error *migration_blocker;
 } BDRVVPCState;
 
 static uint32_t vpc_checksum(uint8_t* buf, size_t size)
@@ -228,6 +231,13 @@ static int vpc_open(BlockDriverState *bs, int flags)
 #endif
 
     qemu_co_mutex_init(&s->lock);
+
+    /* Disable migration when VHD images are used */
+    error_set(&s->migration_blocker,
+              QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED,
+              "vpc", bs->device_name, "live migration");
+    migrate_add_blocker(s->migration_blocker);
+
     return 0;
  fail:
     return err;
@@ -352,8 +362,11 @@ static int64_t alloc_block(BlockDriverState* bs, int64_t sector_num)
 
     // Initialize the block's bitmap
     memset(bitmap, 0xff, s->bitmap_size);
-    bdrv_pwrite_sync(bs->file, s->free_data_block_offset, bitmap,
+    ret = bdrv_pwrite_sync(bs->file, s->free_data_block_offset, bitmap,
         s->bitmap_size);
+    if (ret < 0) {
+        return ret;
+    }
 
     // Write new footer (the old one will be overwritten)
     s->free_data_block_offset += s->block_size + s->bitmap_size;
@@ -651,6 +664,9 @@ static void vpc_close(BlockDriverState *bs)
 #ifdef CACHE
     g_free(s->pageentry_u8);
 #endif
+
+    migrate_del_blocker(s->migration_blocker);
+    error_free(s->migration_blocker);
 }
 
 static QEMUOptionParameter vpc_create_options[] = {
diff --git a/block/vvfat.c b/block/vvfat.c
index 131680f6f4..a310ce8c3e 100644
--- a/block/vvfat.c
+++ b/block/vvfat.c
@@ -27,6 +27,7 @@
 #include "qemu-common.h"
 #include "block_int.h"
 #include "module.h"
+#include "migration.h"
 
 #ifndef S_IWGRP
 #define S_IWGRP 0
@@ -350,6 +351,8 @@ typedef struct BDRVVVFATState {
     array_t commits;
     const char* path;
     int downcase_short_names;
+
+    Error *migration_blocker;
 } BDRVVVFATState;
 
 /* take the sector position spos and convert it to Cylinder/Head/Sector position
@@ -1073,6 +1076,15 @@ DLOG(if (stderr == NULL) {
 
     //    assert(is_consistent(s));
     qemu_co_mutex_init(&s->lock);
+
+    /* Disable migration when vvfat is used rw */
+    if (s->qcow) {
+        error_set(&s->migration_blocker,
+                  QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED,
+                  "vvfat (rw)", bs->device_name, "live migration");
+        migrate_add_blocker(s->migration_blocker);
+    }
+
     return 0;
 }
 
@@ -2829,6 +2841,11 @@ static void vvfat_close(BlockDriverState *bs)
     array_free(&(s->directory));
     array_free(&(s->mapping));
     g_free(s->cluster_buffer);
+
+    if (s->qcow) {
+        migrate_del_blocker(s->migration_blocker);
+        error_free(s->migration_blocker);
+    }
 }
 
 static BlockDriver bdrv_vvfat = {
diff --git a/hw/pci-hotplug.c b/hw/pci-hotplug.c
index b59be2a599..12f61fea6e 100644
--- a/hw/pci-hotplug.c
+++ b/hw/pci-hotplug.c
@@ -91,7 +91,8 @@ static int scsi_hot_add(Monitor *mon, DeviceState *adapter,
      */
     dinfo->unit = qemu_opt_get_number(dinfo->opts, "unit", -1);
     dinfo->bus = scsibus->busnr;
-    scsidev = scsi_bus_legacy_add_drive(scsibus, dinfo->bdrv, dinfo->unit, false);
+    scsidev = scsi_bus_legacy_add_drive(scsibus, dinfo->bdrv, dinfo->unit,
+                                        false, -1);
     if (!scsidev) {
         return -1;
     }
diff --git a/hw/scsi-bus.c b/hw/scsi-bus.c
index 3a2a7bb72c..64e709ee9f 100644
--- a/hw/scsi-bus.c
+++ b/hw/scsi-bus.c
@@ -162,7 +162,7 @@ void scsi_qdev_register(SCSIDeviceInfo *info)
 
 /* handle legacy '-drive if=scsi,...' cmd line args */
 SCSIDevice *scsi_bus_legacy_add_drive(SCSIBus *bus, BlockDriverState *bdrv,
-                                      int unit, bool removable)
+                                      int unit, bool removable, int bootindex)
 {
     const char *driver;
     DeviceState *dev;
@@ -170,6 +170,9 @@ SCSIDevice *scsi_bus_legacy_add_drive(SCSIBus *bus, BlockDriverState *bdrv,
     driver = bdrv_is_sg(bdrv) ? "scsi-generic" : "scsi-disk";
     dev = qdev_create(&bus->qbus, driver);
     qdev_prop_set_uint32(dev, "scsi-id", unit);
+    if (bootindex >= 0) {
+        qdev_prop_set_int32(dev, "bootindex", bootindex);
+    }
     if (qdev_prop_exists(dev, "removable")) {
         qdev_prop_set_bit(dev, "removable", removable);
     }
@@ -195,7 +198,7 @@ int scsi_bus_legacy_handle_cmdline(SCSIBus *bus)
             continue;
         }
         qemu_opts_loc_restore(dinfo->opts);
-        if (!scsi_bus_legacy_add_drive(bus, dinfo->bdrv, unit, false)) {
+        if (!scsi_bus_legacy_add_drive(bus, dinfo->bdrv, unit, false, -1)) {
             res = -1;
             break;
         }
@@ -1367,8 +1370,8 @@ static char *scsibus_get_fw_dev_path(DeviceState *dev)
     SCSIDevice *d = DO_UPCAST(SCSIDevice, qdev, dev);
     char path[100];
 
-    snprintf(path, sizeof(path), "%s@%d,%d,%d", qdev_fw_name(dev),
-             d->channel, d->id, d->lun);
+    snprintf(path, sizeof(path), "channel@%x/%s@%x,%x", d->channel,
+             qdev_fw_name(dev), d->id, d->lun);
 
     return strdup(path);
 }
diff --git a/hw/scsi-generic.c b/hw/scsi-generic.c
index 9594cc1276..e62044f395 100644
--- a/hw/scsi-generic.c
+++ b/hw/scsi-generic.c
@@ -413,6 +413,10 @@ static int scsi_generic_initfn(SCSIDevice *s)
     /* define device state */
     s->type = scsiid.scsi_type;
     DPRINTF("device type %d\n", s->type);
+    if (s->type == TYPE_DISK || s->type == TYPE_ROM) {
+        add_boot_device_path(s->conf.bootindex, &s->qdev, NULL);
+    }
+
     switch (s->type) {
     case TYPE_TAPE:
         s->blocksize = get_stream_blocksize(s->conf.bs);
@@ -459,6 +463,7 @@ static SCSIRequest *scsi_new_request(SCSIDevice *d, uint32_t tag, uint32_t lun,
 
 static SCSIDeviceInfo scsi_generic_info = {
     .qdev.name    = "scsi-generic",
+    .qdev.fw_name = "disk",
     .qdev.desc    = "pass through generic scsi device (/dev/sg*)",
     .qdev.size    = sizeof(SCSIDevice),
     .qdev.reset   = scsi_generic_reset,
diff --git a/hw/scsi.h b/hw/scsi.h
index 61c64d5c72..ab6e952327 100644
--- a/hw/scsi.h
+++ b/hw/scsi.h
@@ -128,7 +128,7 @@ static inline SCSIBus *scsi_bus_from_device(SCSIDevice *d)
 }
 
 SCSIDevice *scsi_bus_legacy_add_drive(SCSIBus *bus, BlockDriverState *bdrv,
-                                      int unit, bool removable);
+                                      int unit, bool removable, int bootindex);
 int scsi_bus_legacy_handle_cmdline(SCSIBus *bus);
 
 /*
diff --git a/hw/usb-msd.c b/hw/usb-msd.c
index 68e3756783..4c06950125 100644
--- a/hw/usb-msd.c
+++ b/hw/usb-msd.c
@@ -546,7 +546,8 @@ static int usb_msd_initfn(USBDevice *dev)
 
     usb_desc_init(dev);
     scsi_bus_new(&s->bus, &s->dev.qdev, &usb_msd_scsi_info);
-    s->scsi_dev = scsi_bus_legacy_add_drive(&s->bus, bs, 0, !!s->removable);
+    s->scsi_dev = scsi_bus_legacy_add_drive(&s->bus, bs, 0, !!s->removable,
+                                            s->conf.bootindex);
     if (!s->scsi_dev) {
         return -1;
     }
@@ -562,7 +563,6 @@ static int usb_msd_initfn(USBDevice *dev)
         }
     }
 
-    add_boot_device_path(s->conf.bootindex, &dev->qdev, "/disk@0,0");
     return 0;
 }
 
diff --git a/hw/virtio-blk.c b/hw/virtio-blk.c
index 19e89e71ee..d6d1f87cda 100644
--- a/hw/virtio-blk.c
+++ b/hw/virtio-blk.c
@@ -485,6 +485,7 @@ static void virtio_blk_update_config(VirtIODevice *vdev, uint8_t *config)
     struct virtio_blk_config blkcfg;
     uint64_t capacity;
     int cylinders, heads, secs;
+    int blk_size = s->conf->logical_block_size;
 
     bdrv_get_geometry(s->bs, &capacity);
     bdrv_get_geometry_hint(s->bs, &cylinders, &heads, &secs);
@@ -492,14 +493,14 @@ static void virtio_blk_update_config(VirtIODevice *vdev, uint8_t *config)
     stq_raw(&blkcfg.capacity, capacity);
     stl_raw(&blkcfg.seg_max, 128 - 2);
     stw_raw(&blkcfg.cylinders, cylinders);
+    stl_raw(&blkcfg.blk_size, blk_size);
+    stw_raw(&blkcfg.min_io_size, s->conf->min_io_size / blk_size);
+    stw_raw(&blkcfg.opt_io_size, s->conf->opt_io_size / blk_size);
     blkcfg.heads = heads;
     blkcfg.sectors = secs & ~s->sector_mask;
-    blkcfg.blk_size = s->conf->logical_block_size;
     blkcfg.size_max = 0;
     blkcfg.physical_block_exp = get_physical_block_exp(s->conf);
     blkcfg.alignment_offset = 0;
-    blkcfg.min_io_size = s->conf->min_io_size / blkcfg.blk_size;
-    blkcfg.opt_io_size = s->conf->opt_io_size / blkcfg.blk_size;
     memcpy(config, &blkcfg, sizeof(struct virtio_blk_config));
 }