WARNING - OLD ARCHIVES

This is an archived copy of the Xen.org mailing list, which we have preserved to ensure that existing links to archives are not broken. The live archive, which contains the latest emails, can be found at http://lists.xen.org/
   
 
 
Xen 
 
Home Products Support Community News
 
   
 

xen-devel

[Xen-devel] [PATCH 08/10] blktap: Set up physical sector size and alignm

To: Xen <xen-devel@xxxxxxxxxxxxxxxxxxx>
Subject: [Xen-devel] [PATCH 08/10] blktap: Set up physical sector size and alignment offsets.
From: Daniel Stodden <daniel.stodden@xxxxxxxxxx>
Date: Tue, 8 Mar 2011 16:42:55 -0800
Cc: Jeremy Fitzhardinge <jeremy@xxxxxxxx>, Daniel Stodden <daniel.stodden@xxxxxxxxxx>
Delivery-date: Tue, 08 Mar 2011 16:51:17 -0800
Envelope-to: www-data@xxxxxxxxxxxxxxxxxxx
In-reply-to: <1299631377-7853-1-git-send-email-daniel.stodden@xxxxxxxxxx>
List-help: <mailto:xen-devel-request@lists.xensource.com?subject=help>
List-id: Xen developer discussion <xen-devel.lists.xensource.com>
List-post: <mailto:xen-devel@lists.xensource.com>
List-subscribe: <http://lists.xensource.com/mailman/listinfo/xen-devel>, <mailto:xen-devel-request@lists.xensource.com?subject=subscribe>
List-unsubscribe: <http://lists.xensource.com/mailman/listinfo/xen-devel>, <mailto:xen-devel-request@lists.xensource.com?subject=unsubscribe>
References: <1299631377-7853-1-git-send-email-daniel.stodden@xxxxxxxxxx>
Sender: xen-devel-bounces@xxxxxxxxxxxxxxxxxxx
Misaligned access wrt to physical block size is a major performance
killer. Alignment offsets is for devices which are 'naturally
misaligned', e.g. to compensate for stuff like DOS 63S/track
partitioning. Accept a BLKTAP_DEVICE_FLAG_PSZ here, and expect
userspace to figure out the physical details.

Signed-off-by: Daniel Stodden <daniel.stodden@xxxxxxxxxx>
---
 drivers/block/blktap/device.c |   37 +++++++++++++++++++++++++++++++++----
 drivers/block/blktap/ring.c   |    4 ++++
 include/linux/blktap.h        |    3 +++
 3 files changed, 40 insertions(+), 4 deletions(-)

diff --git a/drivers/block/blktap/device.c b/drivers/block/blktap/device.c
index fcf16c9..0e8eb0a 100644
--- a/drivers/block/blktap/device.c
+++ b/drivers/block/blktap/device.c
@@ -285,10 +285,13 @@ blktap_device_configure(struct blktap *tap,
        set_capacity(gd, info->capacity);
        set_disk_ro(gd, !!(info->flags & BLKTAP_DEVICE_FLAG_RO));
 
-       /* Hard sector size and max sectors impersonate the equiv. hardware. */
        blk_queue_logical_block_size(rq, info->sector_size);
        blk_queue_max_sectors(rq, 512);
 
+       /* Hard sector size and alignment in hardware */
+       blk_queue_physical_block_size(rq, info->phys_sector_size);
+       blk_queue_alignment_offset(rq, info->phys_sector_offset);
+
        /* Each segment in a request is up to an aligned page in size. */
        blk_queue_segment_boundary(rq, PAGE_SIZE - 1);
        blk_queue_max_segment_size(rq, PAGE_SIZE);
@@ -309,6 +312,7 @@ blktap_device_validate_info(struct blktap *tap,
                            struct blktap_device_info *info)
 {
        struct device *dev = tap->ring.dev;
+       unsigned int phys_mask;
        int sector_order;
 
        sector_order = ffs(info->sector_size) - 1;
@@ -321,11 +325,34 @@ blktap_device_validate_info(struct blktap *tap,
            (info->capacity > ULLONG_MAX >> sector_order))
                goto fail;
 
+       /* physical blocks default to logical ones */
+       if (!(info->flags & BLKTAP_DEVICE_FLAG_PSZ)) {
+               info->phys_sector_size   = info->sector_size;
+               info->phys_sector_offset = 0;
+       }
+
+       /* phys block size is 2^n and >= logical */
+       sector_order = ilog2(info->phys_sector_size);
+       if (sector_order <  9 ||
+           info->phys_sector_size != 1U<<sector_order ||
+           info->phys_sector_size < info->sector_size)
+               goto fail;
+
+       /* alignment offset < physical/logical */
+       phys_mask = (info->phys_sector_size /
+                    info->sector_size) - 1;
+       if ((info->phys_sector_offset & ~phys_mask) != 0)
+               goto fail;
+
        return 0;
 
 fail:
-       dev_err(dev, "capacity: %llu, sector-size: %u\n",
-               info->capacity, info->sector_size);
+       dev_err(dev,
+               "capacity: %llu, sector-size: %u/%u, "
+               "phys-offset: %u\n",
+               info->capacity, info->sector_size,
+               info->phys_sector_size, info->phys_sector_offset);
+
        return -EINVAL;
 }
 
@@ -473,9 +500,11 @@ blktap_device_create(struct blktap *tap, struct 
blktap_device_info *info)
 
        set_bit(BLKTAP_DEVICE, &tap->dev_inuse);
 
-       dev_info(disk_to_dev(gd), "sector-size: %u/%u capacity: %llu\n",
+       dev_info(disk_to_dev(gd),
+                "sector-size: %u/%u phys-offset: %d capacity: %llu\n",
                 queue_logical_block_size(rq),
                 queue_physical_block_size(rq),
+                queue_alignment_offset(rq),
                 (unsigned long long)get_capacity(gd));
 
        return 0;
diff --git a/drivers/block/blktap/ring.c b/drivers/block/blktap/ring.c
index 134583d..25bd311 100644
--- a/drivers/block/blktap/ring.c
+++ b/drivers/block/blktap/ring.c
@@ -446,6 +446,7 @@ blktap_ring_ioctl(struct inode *inode, struct file *filp,
                size_t base_sz, sz;
 
                mask  = BLKTAP_DEVICE_FLAG_RO;
+               mask |= BLKTAP_DEVICE_FLAG_PSZ;
 
                memset(&info, 0, sizeof(info));
                sz = base_sz = BLKTAP_INFO_SIZE_AT(flags);
@@ -453,6 +454,9 @@ blktap_ring_ioctl(struct inode *inode, struct file *filp,
                if (copy_from_user(&info, ptr, sz))
                        return -EFAULT;
 
+               if ((info.flags & BLKTAP_DEVICE_FLAG_PSZ) != 0)
+                       sz = BLKTAP_INFO_SIZE_AT(phys_sector_offset);
+
                if (sz > base_sz)
                        if (copy_from_user(&info, ptr, sz))
                                return -EFAULT;
diff --git a/include/linux/blktap.h b/include/linux/blktap.h
index 2c3c924..9a280d9 100644
--- a/include/linux/blktap.h
+++ b/include/linux/blktap.h
@@ -17,6 +17,7 @@
 #define BLKTAP_IOCTL_REMOVE_DEVICE  207
 
 #define BLKTAP_DEVICE_FLAG_RO       0x00000001UL /* disk is R/O */
+#define BLKTAP_DEVICE_FLAG_PSZ      0x00000002UL /* physical sector size */
 
 struct blktap_info {
        unsigned int            ring_major;
@@ -28,6 +29,8 @@ struct blktap_device_info {
        unsigned long long      capacity;
        unsigned int            sector_size;
        unsigned long           flags;
+       unsigned int            phys_sector_size;
+       unsigned int            phys_sector_offset;
 };
 
 /*
-- 
1.7.0.4


_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-devel

<Prev in Thread] Current Thread [Next in Thread>