Patchwork [1/2] virtio-blk: support VIRTIO_BLK_F_CONFIG_WCE

login
register
mail settings
Submitter Paolo Bonzini
Date July 3, 2012, 1:20 p.m.
Message ID <1341321642-24598-2-git-send-email-pbonzini@redhat.com>
Download mbox | patch
Permalink /patch/168809/
State New
Headers show

Comments

Paolo Bonzini - July 3, 2012, 1:20 p.m.
Introduce a new feature bit and configuration field that provide
support for toggling the cache mode between writethrough and writeback.

Also rename VIRTIO_BLK_F_WCACHE to VIRTIO_BLK_F_WCE for consistency with
the spec.

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
 hw/virtio-blk.c |   16 ++++++++++++++--
 hw/virtio-blk.h |    4 +++-
 2 files changed, 17 insertions(+), 3 deletions(-)
Kevin Wolf - July 3, 2012, 1:46 p.m.
Am 03.07.2012 15:20, schrieb Paolo Bonzini:
> Introduce a new feature bit and configuration field that provide
> support for toggling the cache mode between writethrough and writeback.
> 
> Also rename VIRTIO_BLK_F_WCACHE to VIRTIO_BLK_F_WCE for consistency with
> the spec.

My spec (and my kernel as well) call it VIRTIO_BLK_F_FLUSH.

What's the status of the kernel and spec side of the change?

> 
> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
> ---
>  hw/virtio-blk.c |   16 ++++++++++++++--
>  hw/virtio-blk.h |    4 +++-
>  2 files changed, 17 insertions(+), 3 deletions(-)
> 
> diff --git a/hw/virtio-blk.c b/hw/virtio-blk.c
> index fe07746..280f96d 100644
> --- a/hw/virtio-blk.c
> +++ b/hw/virtio-blk.c
> @@ -510,9 +510,19 @@ static void virtio_blk_update_config(VirtIODevice *vdev, uint8_t *config)
>      blkcfg.size_max = 0;
>      blkcfg.physical_block_exp = get_physical_block_exp(s->conf);
>      blkcfg.alignment_offset = 0;
> +    blkcfg.wce = bdrv_enable_write_cache(s->bs);
>      memcpy(config, &blkcfg, sizeof(struct virtio_blk_config));
>  }
>  
> +static void virtio_blk_set_config(VirtIODevice *vdev, const uint8_t *config)
> +{
> +    VirtIOBlock *s = to_virtio_blk(vdev);
> +    struct virtio_blk_config blkcfg;
> +
> +    memcpy(&blkcfg, config, sizeof(blkcfg));
> +    bdrv_set_enable_write_cache(s->bs, blkcfg.wce != 0);
> +}

We need to call bdrv_flush() here when turning WCE off. And it seems we
don't have a way to signal failure, or may we just leave the bit unchanged?

> @@ -49,6 +50,7 @@ struct virtio_blk_config
>      uint8_t alignment_offset;
>      uint16_t min_io_size;
>      uint32_t opt_io_size;
> +    uint8_t wce;
>  } QEMU_PACKED;

If the spec isn't set in stone yet, we could make it a flags field
instead of using a whole byte for a single flag.

Kevin
Paolo Bonzini - July 3, 2012, 1:54 p.m.
Il 03/07/2012 15:46, Kevin Wolf ha scritto:
>> > Introduce a new feature bit and configuration field that provide
>> > support for toggling the cache mode between writethrough and writeback.
>> > 
>> > Also rename VIRTIO_BLK_F_WCACHE to VIRTIO_BLK_F_WCE for consistency with
>> > the spec.
> My spec (and my kernel as well) call it VIRTIO_BLK_F_FLUSH.
> 
> What's the status of the kernel and spec side of the change?

Both posted.  The spec patch that introduces VIRTIO_BLK_F_CONFIG_WCE
also renames it to VIRTIO_BLK_F_WCE, since that's really what it does.
See this old comment in the kernel (not in the latest git anymore):

       /*
        * If the FLUSH feature is supported we do have support for
        * flushing a volatile write cache on the host.  [...]
        * otherwise, we must assume that the host does not
        * perform any kind of volatile write caching.
        */

Paolo

Patch

diff --git a/hw/virtio-blk.c b/hw/virtio-blk.c
index fe07746..280f96d 100644
--- a/hw/virtio-blk.c
+++ b/hw/virtio-blk.c
@@ -510,9 +510,19 @@  static void virtio_blk_update_config(VirtIODevice *vdev, uint8_t *config)
     blkcfg.size_max = 0;
     blkcfg.physical_block_exp = get_physical_block_exp(s->conf);
     blkcfg.alignment_offset = 0;
+    blkcfg.wce = bdrv_enable_write_cache(s->bs);
     memcpy(config, &blkcfg, sizeof(struct virtio_blk_config));
 }
 
+static void virtio_blk_set_config(VirtIODevice *vdev, const uint8_t *config)
+{
+    VirtIOBlock *s = to_virtio_blk(vdev);
+    struct virtio_blk_config blkcfg;
+
+    memcpy(&blkcfg, config, sizeof(blkcfg));
+    bdrv_set_enable_write_cache(s->bs, blkcfg.wce != 0);
+}
+
 static uint32_t virtio_blk_get_features(VirtIODevice *vdev, uint32_t features)
 {
     VirtIOBlock *s = to_virtio_blk(vdev);
@@ -523,9 +533,10 @@  static uint32_t virtio_blk_get_features(VirtIODevice *vdev, uint32_t features)
     features |= (1 << VIRTIO_BLK_F_BLK_SIZE);
     features |= (1 << VIRTIO_BLK_F_SCSI);
 
+    features |= (1 << VIRTIO_BLK_F_CONFIG_WCE);
     if (bdrv_enable_write_cache(s->bs))
-        features |= (1 << VIRTIO_BLK_F_WCACHE);
-    
+        features |= (1 << VIRTIO_BLK_F_WCE);
+
     if (bdrv_is_read_only(s->bs))
         features |= 1 << VIRTIO_BLK_F_RO;
 
@@ -615,6 +626,7 @@  VirtIODevice *virtio_blk_init(DeviceState *dev, VirtIOBlkConf *blk)
                                           sizeof(VirtIOBlock));
 
     s->vdev.get_config = virtio_blk_update_config;
+    s->vdev.set_config = virtio_blk_set_config;
     s->vdev.get_features = virtio_blk_get_features;
     s->vdev.reset = virtio_blk_reset;
     s->bs = blk->conf.bs;
diff --git a/hw/virtio-blk.h b/hw/virtio-blk.h
index d785001..afea114 100644
--- a/hw/virtio-blk.h
+++ b/hw/virtio-blk.h
@@ -31,8 +31,9 @@ 
 #define VIRTIO_BLK_F_BLK_SIZE   6       /* Block size of disk is available*/
 #define VIRTIO_BLK_F_SCSI       7       /* Supports scsi command passthru */
 /* #define VIRTIO_BLK_F_IDENTIFY   8       ATA IDENTIFY supported, DEPRECATED */
-#define VIRTIO_BLK_F_WCACHE     9       /* write cache enabled */
+#define VIRTIO_BLK_F_WCE        9       /* write cache enabled */
 #define VIRTIO_BLK_F_TOPOLOGY   10      /* Topology information is available */
+#define VIRTIO_BLK_F_CONFIG_WCE 11      /* write cache configurable */
 
 #define VIRTIO_BLK_ID_BYTES     20      /* ID string length */
 
@@ -49,6 +50,7 @@  struct virtio_blk_config
     uint8_t alignment_offset;
     uint16_t min_io_size;
     uint32_t opt_io_size;
+    uint8_t wce;
 } QEMU_PACKED;
 
 /* These two define direction. */