aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rwxr-xr-xconfigure20
-rw-r--r--hw/block/dataplane/xen-block.c4
-rw-r--r--hw/block/trace-events1
-rw-r--r--hw/block/xen-block.c40
-rw-r--r--hw/xen/xen-bus.c32
5 files changed, 57 insertions, 40 deletions
diff --git a/configure b/configure
index f8176b3..3d89870 100755
--- a/configure
+++ b/configure
@@ -2359,7 +2359,6 @@ if test "$xen" != "no" ; then
fi
QEMU_CFLAGS="$QEMU_CFLAGS $($pkg_config --cflags $xen_pc)"
libs_softmmu="$($pkg_config --libs $xen_pc) $libs_softmmu"
- LDFLAGS="$($pkg_config --libs $xen_pc) $LDFLAGS"
else
xen_libs="-lxenstore -lxenctrl -lxenguest"
@@ -2474,7 +2473,6 @@ int main(void) {
xenforeignmemory_handle *xfmem;
xenevtchn_handle *xe;
xengnttab_handle *xg;
- xen_domain_handle_t handle;
xengnttab_grant_copy_segment_t* seg = NULL;
xs_daemon_open();
@@ -2484,7 +2482,6 @@ int main(void) {
xc_domain_add_to_physmap(0, 0, XENMAPSPACE_gmfn, 0, 0);
xc_hvm_inject_msi(xc, 0, 0xf0000000, 0x00000000);
xc_hvm_create_ioreq_server(xc, 0, HVM_IOREQSRV_BUFIOREQ_ATOMIC, NULL);
- xc_domain_create(xc, 0, handle, 0, NULL, NULL);
xfmem = xenforeignmemory_open(0, 0);
xenforeignmemory_map(xfmem, 0, 0, 0, 0, 0);
@@ -2526,7 +2523,6 @@ int main(void) {
xenforeignmemory_handle *xfmem;
xenevtchn_handle *xe;
xengnttab_handle *xg;
- xen_domain_handle_t handle;
xs_daemon_open();
@@ -2535,7 +2531,6 @@ int main(void) {
xc_domain_add_to_physmap(0, 0, XENMAPSPACE_gmfn, 0, 0);
xc_hvm_inject_msi(xc, 0, 0xf0000000, 0x00000000);
xc_hvm_create_ioreq_server(xc, 0, HVM_IOREQSRV_BUFIOREQ_ATOMIC, NULL);
- xc_domain_create(xc, 0, handle, 0, NULL, NULL);
xfmem = xenforeignmemory_open(0, 0);
xenforeignmemory_map(xfmem, 0, 0, 0, 0, 0);
@@ -2553,21 +2548,6 @@ EOF
then
xen_ctrl_version=40701
xen=yes
- elif
- cat > $TMPC <<EOF &&
-#include <xenctrl.h>
-#include <stdint.h>
-int main(void) {
- xc_interface *xc = NULL;
- xen_domain_handle_t handle;
- xc_domain_create(xc, 0, handle, 0, NULL, NULL);
- return 0;
-}
-EOF
- compile_prog "" "$xen_libs"
- then
- xen_ctrl_version=40700
- xen=yes
# Xen 4.6
elif
diff --git a/hw/block/dataplane/xen-block.c b/hw/block/dataplane/xen-block.c
index d0d8905..c6a15da 100644
--- a/hw/block/dataplane/xen-block.c
+++ b/hw/block/dataplane/xen-block.c
@@ -50,7 +50,6 @@ struct XenBlockDataPlane {
unsigned int nr_ring_ref;
void *sring;
int64_t file_blk;
- int64_t file_size;
int protocol;
blkif_back_rings_t rings;
int more_work;
@@ -189,7 +188,7 @@ static int xen_block_parse_request(XenBlockRequest *request)
request->req.seg[i].first_sect + 1) * dataplane->file_blk;
request->size += len;
}
- if (request->start + request->size > dataplane->file_size) {
+ if (request->start + request->size > blk_getlength(dataplane->blk)) {
error_report("error: access beyond end of file");
goto err;
}
@@ -638,7 +637,6 @@ XenBlockDataPlane *xen_block_dataplane_create(XenDevice *xendev,
dataplane->xendev = xendev;
dataplane->file_blk = conf->logical_block_size;
dataplane->blk = conf->blk;
- dataplane->file_size = blk_getlength(dataplane->blk);
QLIST_INIT(&dataplane->inflight);
QLIST_INIT(&dataplane->freelist);
diff --git a/hw/block/trace-events b/hw/block/trace-events
index d085195..8020f92 100644
--- a/hw/block/trace-events
+++ b/hw/block/trace-events
@@ -126,6 +126,7 @@ xen_block_realize(const char *type, uint32_t disk, uint32_t partition) "%s d%up%
xen_block_connect(const char *type, uint32_t disk, uint32_t partition) "%s d%up%u"
xen_block_disconnect(const char *type, uint32_t disk, uint32_t partition) "%s d%up%u"
xen_block_unrealize(const char *type, uint32_t disk, uint32_t partition) "%s d%up%u"
+xen_block_size(const char *type, uint32_t disk, uint32_t partition, int64_t sectors) "%s d%up%u %"PRIi64
xen_disk_realize(void) ""
xen_disk_unrealize(void) ""
xen_cdrom_realize(void) ""
diff --git a/hw/block/xen-block.c b/hw/block/xen-block.c
index a636487..5012af9 100644
--- a/hw/block/xen-block.c
+++ b/hw/block/xen-block.c
@@ -144,6 +144,38 @@ static void xen_block_unrealize(XenDevice *xendev, Error **errp)
}
}
+static void xen_block_set_size(XenBlockDevice *blockdev)
+{
+ const char *type = object_get_typename(OBJECT(blockdev));
+ XenBlockVdev *vdev = &blockdev->props.vdev;
+ BlockConf *conf = &blockdev->props.conf;
+ int64_t sectors = blk_getlength(conf->blk) / conf->logical_block_size;
+ XenDevice *xendev = XEN_DEVICE(blockdev);
+
+ trace_xen_block_size(type, vdev->disk, vdev->partition, sectors);
+
+ xen_device_backend_printf(xendev, "sectors", "%"PRIi64, sectors);
+}
+
+static void xen_block_resize_cb(void *opaque)
+{
+ XenBlockDevice *blockdev = opaque;
+ XenDevice *xendev = XEN_DEVICE(blockdev);
+ enum xenbus_state state = xen_device_backend_get_state(xendev);
+
+ xen_block_set_size(blockdev);
+
+ /*
+ * Mimic the behaviour of Linux xen-blkback and re-write the state
+ * to trigger the frontend watch.
+ */
+ xen_device_backend_printf(xendev, "state", "%u", state);
+}
+
+static const BlockDevOps xen_block_dev_ops = {
+ .resize_cb = xen_block_resize_cb,
+};
+
static void xen_block_realize(XenDevice *xendev, Error **errp)
{
XenBlockDevice *blockdev = XEN_BLOCK_DEVICE(xendev);
@@ -180,7 +212,7 @@ static void xen_block_realize(XenDevice *xendev, Error **errp)
}
if (!blkconf_apply_backend_options(conf, blockdev->info & VDISK_READONLY,
- false, errp)) {
+ true, errp)) {
return;
}
@@ -197,6 +229,7 @@ static void xen_block_realize(XenDevice *xendev, Error **errp)
return;
}
+ blk_set_dev_ops(conf->blk, &xen_block_dev_ops, blockdev);
blk_set_guest_block_size(conf->blk, conf->logical_block_size);
if (conf->discard_granularity > 0) {
@@ -215,9 +248,8 @@ static void xen_block_realize(XenDevice *xendev, Error **errp)
xen_device_backend_printf(xendev, "sector-size", "%u",
conf->logical_block_size);
- xen_device_backend_printf(xendev, "sectors", "%"PRIi64,
- blk_getlength(conf->blk) /
- conf->logical_block_size);
+
+ xen_block_set_size(blockdev);
blockdev->dataplane =
xen_block_dataplane_create(xendev, conf, blockdev->props.iothread);
diff --git a/hw/xen/xen-bus.c b/hw/xen/xen-bus.c
index 3aeccec..49a725e 100644
--- a/hw/xen/xen-bus.c
+++ b/hw/xen/xen-bus.c
@@ -547,20 +547,15 @@ static void xen_device_backend_changed(void *opaque)
}
/*
- * If a backend is still 'online' then its state should be cycled
- * back round to InitWait in order for a new frontend instance to
- * connect. This may happen when, for example, a frontend driver is
- * re-installed or updated.
- * If a backend is not 'online' then the device should be destroyed.
+ * If a backend is still 'online' then we should leave it alone but,
+ * if a backend is not 'online', then the device should be destroyed
+ * once the state is Closed.
*/
- if (xendev->backend_online &&
- xendev->backend_state == XenbusStateClosed) {
- xen_device_backend_set_state(xendev, XenbusStateInitWait);
- } else if (!xendev->backend_online &&
- (xendev->backend_state == XenbusStateClosed ||
- xendev->backend_state == XenbusStateInitialising ||
- xendev->backend_state == XenbusStateInitWait ||
- xendev->backend_state == XenbusStateUnknown)) {
+ if (!xendev->backend_online &&
+ (xendev->backend_state == XenbusStateClosed ||
+ xendev->backend_state == XenbusStateInitialising ||
+ xendev->backend_state == XenbusStateInitWait ||
+ xendev->backend_state == XenbusStateUnknown)) {
Error *local_err = NULL;
if (!xen_backend_try_device_destroy(xendev, &local_err)) {
@@ -715,6 +710,17 @@ static void xen_device_frontend_changed(void *opaque)
xen_device_frontend_set_state(xendev, state);
+ if (state == XenbusStateInitialising &&
+ xendev->backend_state == XenbusStateClosed &&
+ xendev->backend_online) {
+ /*
+ * The frontend is re-initializing so switch back to
+ * InitWait.
+ */
+ xen_device_backend_set_state(xendev, XenbusStateInitWait);
+ return;
+ }
+
if (xendev_class->frontend_changed) {
Error *local_err = NULL;