Sophie

Sophie

distrib > Scientific%20Linux > 5x > x86_64 > by-pkgid > 3160499aacb81f6735941eb4c372d87a > files > 236

kvm-83-164.el5_5.30.src.rpm

From 50ea6e9df1ae6ec1f3c89c466a21c27e63935060 Mon Sep 17 00:00:00 2001
From: Kevin Wolf <kwolf@redhat.com>
Date: Tue, 6 Jul 2010 09:51:53 -0300
Subject: [PATCH 17/18] block: Add bdrv_(p)write_sync

RH-Author: Kevin Wolf <kwolf@redhat.com>
Message-id: <1278409914-12193-2-git-send-email-kwolf@redhat.com>
Patchwork-id: 10492
O-Subject: [RHEL-5.5.z KVM PATCH v3 1/2] block: Add bdrv_(p)write_sync
Bugzilla: 612507
RH-Acked-by: Juan Quintela <quintela@redhat.com>
RH-Acked-by: Christoph Hellwig <chellwig@redhat.com>
RH-Acked-by: Jes Sorensen <Jes.Sorensen@redhat.com>

Bugzilla: 572825
Upstream commit: f08145fe16470aca09304099888f68cfbc5d1de7

Add new functions that write and flush the written data to disk immediately.
This is what needs to be used for image format metadata to maintain integrity
for cache=... modes that don't use O_DSYNC. (Actually, we only need barriers,
and therefore the functions are defined as such, but flushes is what is
implemented in this patch - we can try to change that later)

Signed-off-by: Kevin Wolf <kwolf@redhat.com>
---
 qemu/block.c     |   39 +++++++++++++++++++++++++++++++++++++++
 qemu/block.h     |    4 ++++
 qemu/block_int.h |    1 +
 3 files changed, 44 insertions(+), 0 deletions(-)

Signed-off-by: Eduardo Habkost <ehabkost@redhat.com>
---
 qemu/block.c     |   39 +++++++++++++++++++++++++++++++++++++++
 qemu/block.h     |    4 ++++
 qemu/block_int.h |    1 +
 3 files changed, 44 insertions(+), 0 deletions(-)

diff --git a/qemu/block.c b/qemu/block.c
index 7d5c225..395df1a 100644
--- a/qemu/block.c
+++ b/qemu/block.c
@@ -495,6 +495,8 @@ int bdrv_open2(BlockDriverState *bs, const char *filename, int flags,
         open_flags = BDRV_O_RDWR | (flags & BDRV_O_CACHE_MASK);
     else
         open_flags = flags & ~(BDRV_O_FILE | BDRV_O_SNAPSHOT);
+
+    bs->open_flags = open_flags;
     if (only_supported_bdrv && !bdrv_is_supported(drv))
         ret = -ENOTSUP;
     else
@@ -892,6 +894,43 @@ int bdrv_pwrite(BlockDriverState *bs, int64_t offset,
     return drv->bdrv_pwrite(bs, offset, buf1, count1);
 }
 
+/*
+ * Writes to the file and ensures that no writes are reordered across this
+ * request (acts as a barrier)
+ *
+ * Returns 0 on success, -errno in error cases.
+ */
+int bdrv_pwrite_sync(BlockDriverState *bs, int64_t offset,
+    const void *buf, int count)
+{
+    int ret;
+
+    ret = bdrv_pwrite(bs, offset, buf, count);
+    if (ret < 0) {
+        return ret;
+    }
+
+    /* No flush needed for cache=writethrough, it uses O_DSYNC */
+    if ((bs->open_flags & BDRV_O_CACHE_MASK) != 0) {
+        bdrv_flush(bs);
+    }
+
+    return 0;
+}
+
+/*
+ * Writes to the file and ensures that no writes are reordered across this
+ * request (acts as a barrier)
+ *
+ * Returns 0 on success, -errno in error cases.
+ */
+int bdrv_write_sync(BlockDriverState *bs, int64_t sector_num,
+    const uint8_t *buf, int nb_sectors)
+{
+    return bdrv_pwrite_sync(bs, 512 * sector_num,
+        buf, 512 * nb_sectors);
+}
+
 /**
  * Truncate file to 'offset' bytes (needed only for file protocols)
  */
diff --git a/qemu/block.h b/qemu/block.h
index 753b356..0c6d984 100644
--- a/qemu/block.h
+++ b/qemu/block.h
@@ -81,6 +81,10 @@ int bdrv_pread(BlockDriverState *bs, int64_t offset,
                void *buf, int count);
 int bdrv_pwrite(BlockDriverState *bs, int64_t offset,
                 const void *buf, int count);
+int bdrv_pwrite_sync(BlockDriverState *bs, int64_t offset,
+    const void *buf, int count);
+int bdrv_write_sync(BlockDriverState *bs, int64_t sector_num,
+    const uint8_t *buf, int nb_sectors);
 int bdrv_truncate(BlockDriverState *bs, int64_t offset);
 int64_t bdrv_getlength(BlockDriverState *bs);
 void bdrv_get_geometry(BlockDriverState *bs, uint64_t *nb_sectors_ptr);
diff --git a/qemu/block_int.h b/qemu/block_int.h
index 2f8093c..43a4e6a 100644
--- a/qemu/block_int.h
+++ b/qemu/block_int.h
@@ -112,6 +112,7 @@ struct BlockDriverState {
     int64_t total_sectors; /* if we are reading a disk image, give its
                               size in sectors */
     int read_only; /* if true, the media is read only */
+    int open_flags; /* flags used to open the file, re-used for re-open */
     int removable; /* if true, the media can be removed */
     int locked;    /* if true, the media cannot temporarily be ejected */
     int encrypted; /* if true, the media is encrypted */
-- 
1.7.0.3