]> xenbits.xensource.com Git - people/dstodden/blktap.git/commitdiff
use fallocate when possible for allocating vhd blocks xcp/volatile/ext4
authorJake Wires <Jake.Wires@citrix.com>
Tue, 31 May 2011 23:07:03 +0000 (16:07 -0700)
committerDaniel Stodden <daniel.stodden@citrix.com>
Tue, 30 Aug 2011 13:51:45 +0000 (14:51 +0100)
[Forward port from xc/master abb20c8]
Signed-off-by: Daniel Stodden <daniel.stodden@citrix.com>
drivers/block-vhd.c

index 0e0bf2cc3479e964a246b853a70d503ad335ca8f..9e6870b9032f2f7116437c65f6343ce12a4d9833 100644 (file)
@@ -62,6 +62,7 @@
 #include <string.h>    /* for memset.                                 */
 #include <libaio.h>
 #include <sys/mman.h>
+#include <sys/syscall.h>
 
 #include "libvhd.h"
 #include "tapdisk.h"
@@ -1465,6 +1466,12 @@ update_bat(struct vhd_state *s, uint32_t blk)
        return 0;
 }
 
+static int
+vhd_fallocate(int fd, int mode, off_t offset, off_t length)
+{
+       return syscall(SYS_fallocate, fd, mode, offset, length);
+}
+
 static int
 allocate_block(struct vhd_state *s, uint32_t blk)
 {
@@ -1493,25 +1500,34 @@ allocate_block(struct vhd_state *s, uint32_t blk)
        }
 
        s->bat.pbw_offset = s->next_db;
+       size = vhd_sectors_to_bytes(s->spb + s->bm_secs + gap);
 
        DBG(TLOG_DBG, "blk: 0x%04x, pbwo: 0x%08"PRIx64"\n",
            blk, s->bat.pbw_offset);
 
-       if (lseek(s->vhd.fd, offset, SEEK_SET) == (off_t)-1) {
-               ERR(s, -errno, "lseek failed\n");
-               return -errno;
-       }
+       err = vhd_fallocate(s->vhd.fd, 0, offset, size);
+       if (err) {
+               if (errno != ENOSYS) {
+                       ERR(s, -errno, "fallocate failed\n");
+                       return -errno;
+               }
 
-       size  = vhd_sectors_to_bytes(s->spb + s->bm_secs + gap);
-       count = write(s->vhd.fd, vhd_zeros(size), size);
-       if (count != size) {
-               err = count < 0 ? -errno : -ENOSPC;
-               ERR(s, -errno,
-                   "write failed (%zd, offset %"PRIu64")\n", count, offset);
-               return err;
+               if (lseek(s->vhd.fd, offset, SEEK_SET) == (off_t)-1) {
+                       ERR(s, -errno, "lseek failed\n");
+                       return -errno;
+               }
+
+               count = write(s->vhd.fd, vhd_zeros(size), size);
+               if (count != size) {
+                       err = count < 0 ? -errno : -ENOSPC;
+                       ERR(s, -errno,
+                           "write failed (%zd, offset %"PRIu64")\n",
+                           count, offset);
+                       return err;
+               }
        }
 
-       err  = fdatasync(s->vhd.fd);
+       err = fdatasync(s->vhd.fd);
        if (err) {
                err = -errno;
                ERR(s, err, "sync failed");