From: George Kennedy Date: Wed, 15 Feb 2017 20:17:58 +0000 (-0500) Subject: SPARC64: vds_blk_rw() does not handle drives with q->limits.chunk_sectors > 0 X-Git-Tag: v4.1.12-98.0.20170517_2143~37^2~2 X-Git-Url: https://www.infradead.org/git/?a=commitdiff_plain;h=782dd8bbc86912c26d3a5ae1bbdebbd54b460725;p=users%2Fjedix%2Flinux-maple.git SPARC64: vds_blk_rw() does not handle drives with q->limits.chunk_sectors > 0 Drives with q->limits.chunk_sectors > 0 are not properly handled by vds_blk_rw(). Drives such as NVME set chunk_sectors to indicate a performance boundary (see call to blk_queue_chunk_sectors() in nvme_alloc_ns()). Currently, when vds_blk_rw() calls bio_add_page() and the chunk_sectors boundary would be crossed, bio_add_page() returns zero and vds_blk_rw() fails with -EIO. The proposed fix now adds an additional check to vds_blk_rw() when bio_add_page() returns zero that checks for bio->bi_iter.bi_size != 0. If bi_size != 0, it indicates that a page or pages have been successfully added by bio_add_page(). When this added condition has been hit, exit the for loop in vds_blk_rw() and submit the outstanding IOs and continue. Signed-off-by: George Kennedy Reviewed-By: Bijan Mottahedeh Reviewed-By: Liam Merwick Orabug: 25373818 Signed-off-by: Allen Pais --- diff --git a/drivers/block/vds/vds_blk.c b/drivers/block/vds/vds_blk.c index 9cc1635f3dee9..e650294d45209 100644 --- a/drivers/block/vds/vds_blk.c +++ b/drivers/block/vds/vds_blk.c @@ -1,7 +1,7 @@ /* * vds_blk.c: LDOM Virtual Disk Server. * - * Copyright (C) 2014, 2016 Oracle. All rights reserved. + * Copyright (C) 2014, 2017 Oracle. All rights reserved. */ #include "vds.h" @@ -149,9 +149,19 @@ static int vds_blk_rw(struct vds_io *io) bio->bi_iter.bi_sector, bio->bi_iter.bi_size); if (!rv) { + /* + * A drive with chunk_sectors > 0 (i.e. NVME) + * will result in rv = 0 when the chunk_sectors + * boundary has been hit. Break here if page(s) + * have already been added (bi_size != 0). + * Submit the already added pages and continue. + */ + if (bio->bi_iter.bi_size != 0) + break; vdsmsg(err, - "bio_add_page: resid=%ld biolen=%ld\n", - resid, biolen); + "bio_add_page: resid=%ld biolen=%ld " + "bi_sector=%ld\n", + resid, biolen, bio->bi_iter.bi_sector); err = -EIO; break; }