[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Xen-devel] [PATCH 05/10] blktap: Support non-R/W requests



Special cases segment vector writes on the blktap ring. Anticipate
non-fs requests on the queue. Add some switches, for trim or flush
operations to settle.

Signed-off-by: Daniel Stodden <daniel.stodden@xxxxxxxxxx>
---
 drivers/block/blktap/device.c |   24 ++++++--------
 drivers/block/blktap/ring.c   |   68 +++++++++++++++++++++++++---------------
 2 files changed, 53 insertions(+), 39 deletions(-)

diff --git a/drivers/block/blktap/device.c b/drivers/block/blktap/device.c
index 8caff9f..fcf16c9 100644
--- a/drivers/block/blktap/device.c
+++ b/drivers/block/blktap/device.c
@@ -166,7 +166,7 @@ blktap_device_make_request(struct blktap *tap, struct 
request *rq)
 {
        struct blktap_device *tapdev = &tap->device;
        struct blktap_request *request;
-       int write, nsegs;
+       int nsegs;
        int err;
 
        request = blktap_ring_make_request(tap);
@@ -180,15 +180,17 @@ blktap_device_make_request(struct blktap *tap, struct 
request *rq)
                goto fail;
        }
 
-       write = rq_data_dir(rq) == WRITE;
+       if (!blk_fs_request(rq)) {
+               err = -EOPNOTSUPP;
+               goto fail;
+       }
+
        nsegs = blk_rq_map_sg(rq->q, rq, request->sg_table);
 
-       dev_dbg(disk_to_dev(tapdev->gd),
-               "make_request: op=%c bytes=%d nsegs=%d\n",
-               write ? 'w' : 'r', blk_rq_bytes(rq), nsegs);
-
-       request->rq = rq;
-       request->operation = write ? BLKTAP_OP_WRITE : BLKTAP_OP_READ;
+       if (rq_data_dir(rq) == WRITE)
+               request->operation = BLKTAP_OP_WRITE;
+       else
+               request->operation = BLKTAP_OP_READ;
 
        err = blktap_request_get_pages(tap, request, nsegs);
        if (err)
@@ -198,6 +200,7 @@ blktap_device_make_request(struct blktap *tap, struct 
request *rq)
        if (err)
                goto fail;
 
+       request->rq = rq;
        blktap_ring_submit_request(tap, request);
 
        return 0;
@@ -242,11 +245,6 @@ blktap_device_run_queue(struct blktap *tap)
                if (!rq)
                        break;
 
-               if (!blk_fs_request(rq)) {
-                       __blktap_end_queued_rq(rq, -EOPNOTSUPP);
-                       continue;
-               }
-
                spin_unlock_irq(&tapdev->lock);
 
                err = blktap_device_make_request(tap, rq);
diff --git a/drivers/block/blktap/ring.c b/drivers/block/blktap/ring.c
index 635f1fd..bae6f82 100644
--- a/drivers/block/blktap/ring.c
+++ b/drivers/block/blktap/ring.c
@@ -241,14 +241,39 @@ blktap_ring_make_request(struct blktap *tap)
        return request;
 }
 
+static int
+blktap_ring_make_rw_request(struct blktap *tap,
+                           struct blktap_request *request,
+                           struct blktap_ring_request *breq)
+{
+       struct scatterlist *sg;
+       unsigned int i, nsecs = 0;
+
+       blktap_for_each_sg(sg, request, i) {
+               struct blktap_segment *seg = &breq->seg[i];
+               int first, count;
+
+               count = sg->length >> 9;
+               first = sg->offset >> 9;
+
+               seg->first_sect = first;
+               seg->last_sect  = first + count - 1;
+
+               nsecs += count;
+       }
+
+       breq->sector_number = blk_rq_pos(request->rq);
+
+       return nsecs;
+}
+
 void
 blktap_ring_submit_request(struct blktap *tap,
                           struct blktap_request *request)
 {
        struct blktap_ring *ring = &tap->ring;
        blktap_ring_req_t *breq;
-       struct scatterlist *sg;
-       int i, nsecs = 0;
+       int nsecs;
 
        dev_dbg(ring->dev,
                "request %d [%p] submit\n", request->usr_idx, request);
@@ -256,38 +281,31 @@ blktap_ring_submit_request(struct blktap *tap,
        breq = RING_GET_REQUEST(&ring->ring, ring->ring.req_prod_pvt);
 
        breq->id            = request->usr_idx;
-       breq->sector_number = blk_rq_pos(request->rq);
        breq->__pad         = 0;
        breq->operation     = request->operation;
        breq->nr_segments   = request->nr_pages;
 
-       blktap_for_each_sg(sg, request, i) {
-               struct blktap_segment *seg = &breq->seg[i];
-               int first, count;
+       switch (breq->operation) {
+       case BLKTAP_OP_READ:
+               nsecs = blktap_ring_make_rw_request(tap, request, breq);
 
-               count = sg->length >> 9;
-               first = sg->offset >> 9;
+               tap->stats.st_rd_sect += nsecs;
+               tap->stats.st_rd_req++;
+               break;
 
-               seg->first_sect = first;
-               seg->last_sect  = first + count - 1;
+       case BLKTAP_OP_WRITE:
+               nsecs = blktap_ring_make_rw_request(tap, request, breq);
 
-               nsecs += count;
+               tap->stats.st_wr_sect += nsecs;
+               tap->stats.st_wr_req++;
+               break;
+       default:
+               BUG();
        }
 
        ring->ring.req_prod_pvt++;
 
        do_gettimeofday(&request->time);
-
-
-       if (request->operation == BLKTAP_OP_WRITE) {
-               tap->stats.st_wr_sect += nsecs;
-               tap->stats.st_wr_req++;
-       }
-
-       if (request->operation == BLKTAP_OP_READ) {
-               tap->stats.st_rd_sect += nsecs;
-               tap->stats.st_rd_req++;
-       }
 }
 
 static int
@@ -530,20 +548,18 @@ blktap_ring_debug(struct blktap *tap, char *buf, size_t 
size)
        for (usr_idx = 0; usr_idx < BLKTAP_RING_SIZE; usr_idx++) {
                struct blktap_request *request;
                struct timeval *time;
-               int write;
 
                request = ring->pending[usr_idx];
                if (!request)
                        continue;
 
-               write = request->operation == BLKTAP_OP_WRITE;
                time  = &request->time;
 
                s += snprintf(s, end - s,
                              "%02d: usr_idx:%02d "
-                             "op:%c nr_pages:%02d time:%lu.%09lu\n",
+                             "op:%x nr_pages:%02d time:%lu.%09lu\n",
                              usr_idx, request->usr_idx,
-                             write ? 'W' : 'R', request->nr_pages,
+                             request->operation, request->nr_pages,
                              time->tv_sec, time->tv_usec);
        }
 
-- 
1.7.0.4


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


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.