xen/blkback: Move processing of BLKIF_OP_DISCARD from dispatch_rw_block_io
.. and move it to its own function that will deal with the discard operation. Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
This commit is contained in:
parent
5ea4298669
commit
421463526f
|
@ -416,12 +416,16 @@ static int xen_blkbk_map(struct blkif_request *req,
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void xen_blk_discard(struct xen_blkif *blkif, struct blkif_request *req)
|
static int dispatch_discard_io(struct xen_blkif *blkif,
|
||||||
|
struct blkif_request *req)
|
||||||
{
|
{
|
||||||
int err = 0;
|
int err = 0;
|
||||||
int status = BLKIF_RSP_OKAY;
|
int status = BLKIF_RSP_OKAY;
|
||||||
struct block_device *bdev = blkif->vbd.bdev;
|
struct block_device *bdev = blkif->vbd.bdev;
|
||||||
|
|
||||||
|
blkif->st_ds_req++;
|
||||||
|
|
||||||
|
xen_blkif_get(blkif);
|
||||||
if (blkif->blk_backend_type == BLKIF_BACKEND_PHY) {
|
if (blkif->blk_backend_type == BLKIF_BACKEND_PHY) {
|
||||||
unsigned long secure = (blkif->vbd.discard_secure &&
|
unsigned long secure = (blkif->vbd.discard_secure &&
|
||||||
(req->u.discard.flag & BLKIF_DISCARD_SECURE)) ?
|
(req->u.discard.flag & BLKIF_DISCARD_SECURE)) ?
|
||||||
|
@ -453,6 +457,8 @@ static void xen_blk_discard(struct xen_blkif *blkif, struct blkif_request *req)
|
||||||
status = BLKIF_RSP_ERROR;
|
status = BLKIF_RSP_ERROR;
|
||||||
|
|
||||||
make_response(blkif, req->u.discard.id, req->operation, status);
|
make_response(blkif, req->u.discard.id, req->operation, status);
|
||||||
|
xen_blkif_put(blkif);
|
||||||
|
return err;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void xen_blk_drain_io(struct xen_blkif *blkif)
|
static void xen_blk_drain_io(struct xen_blkif *blkif)
|
||||||
|
@ -576,8 +582,11 @@ __do_block_io_op(struct xen_blkif *blkif)
|
||||||
|
|
||||||
/* Apply all sanity checks to /private copy/ of request. */
|
/* Apply all sanity checks to /private copy/ of request. */
|
||||||
barrier();
|
barrier();
|
||||||
|
if (unlikely(req.operation == BLKIF_OP_DISCARD)) {
|
||||||
if (dispatch_rw_block_io(blkif, &req, pending_req))
|
free_req(pending_req);
|
||||||
|
if (dispatch_discard_io(blkif, &req))
|
||||||
|
break;
|
||||||
|
} else if (dispatch_rw_block_io(blkif, &req, pending_req))
|
||||||
break;
|
break;
|
||||||
|
|
||||||
/* Yield point for this unbounded loop. */
|
/* Yield point for this unbounded loop. */
|
||||||
|
@ -636,24 +645,16 @@ static int dispatch_rw_block_io(struct xen_blkif *blkif,
|
||||||
blkif->st_f_req++;
|
blkif->st_f_req++;
|
||||||
operation = WRITE_FLUSH;
|
operation = WRITE_FLUSH;
|
||||||
break;
|
break;
|
||||||
case BLKIF_OP_DISCARD:
|
|
||||||
blkif->st_ds_req++;
|
|
||||||
operation = REQ_DISCARD;
|
|
||||||
break;
|
|
||||||
default:
|
default:
|
||||||
operation = 0; /* make gcc happy */
|
operation = 0; /* make gcc happy */
|
||||||
goto fail_response;
|
goto fail_response;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (unlikely(operation == REQ_DISCARD))
|
/* Check that the number of segments is sane. */
|
||||||
nseg = 0;
|
nseg = req->u.rw.nr_segments;
|
||||||
else
|
|
||||||
/* Check that the number of segments is sane. */
|
|
||||||
nseg = req->u.rw.nr_segments;
|
|
||||||
|
|
||||||
if (unlikely(nseg == 0 && operation != WRITE_FLUSH &&
|
if (unlikely(nseg == 0 && operation != WRITE_FLUSH) ||
|
||||||
operation != REQ_DISCARD) ||
|
|
||||||
unlikely(nseg > BLKIF_MAX_SEGMENTS_PER_REQUEST)) {
|
unlikely(nseg > BLKIF_MAX_SEGMENTS_PER_REQUEST)) {
|
||||||
pr_debug(DRV_PFX "Bad number of segments in request (%d)\n",
|
pr_debug(DRV_PFX "Bad number of segments in request (%d)\n",
|
||||||
nseg);
|
nseg);
|
||||||
|
@ -714,7 +715,7 @@ static int dispatch_rw_block_io(struct xen_blkif *blkif,
|
||||||
* the hypercall to unmap the grants - that is all done in
|
* the hypercall to unmap the grants - that is all done in
|
||||||
* xen_blkbk_unmap.
|
* xen_blkbk_unmap.
|
||||||
*/
|
*/
|
||||||
if (nseg && xen_blkbk_map(req, pending_req, seg))
|
if (xen_blkbk_map(req, pending_req, seg))
|
||||||
goto fail_flush;
|
goto fail_flush;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -746,23 +747,16 @@ static int dispatch_rw_block_io(struct xen_blkif *blkif,
|
||||||
|
|
||||||
/* This will be hit if the operation was a flush or discard. */
|
/* This will be hit if the operation was a flush or discard. */
|
||||||
if (!bio) {
|
if (!bio) {
|
||||||
BUG_ON(operation != WRITE_FLUSH && operation != REQ_DISCARD);
|
BUG_ON(operation != WRITE_FLUSH);
|
||||||
|
|
||||||
if (operation == WRITE_FLUSH) {
|
bio = bio_alloc(GFP_KERNEL, 0);
|
||||||
bio = bio_alloc(GFP_KERNEL, 0);
|
if (unlikely(bio == NULL))
|
||||||
if (unlikely(bio == NULL))
|
goto fail_put_bio;
|
||||||
goto fail_put_bio;
|
|
||||||
|
|
||||||
biolist[nbio++] = bio;
|
biolist[nbio++] = bio;
|
||||||
bio->bi_bdev = preq.bdev;
|
bio->bi_bdev = preq.bdev;
|
||||||
bio->bi_private = pending_req;
|
bio->bi_private = pending_req;
|
||||||
bio->bi_end_io = end_block_io_op;
|
bio->bi_end_io = end_block_io_op;
|
||||||
} else if (operation == REQ_DISCARD) {
|
|
||||||
xen_blk_discard(blkif, req);
|
|
||||||
xen_blkif_put(blkif);
|
|
||||||
free_req(pending_req);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
Loading…
Reference in New Issue