linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Dmitry Monakhov <dmonakhov@openvz.org>
To: linux-kernel@vger.kernel.org, linux-block@vger.kernel.org,
	martin.petersen@oracle.com
Cc: Dmitry Monakhov <dmonakhov@openvz.org>
Subject: [PATCH 7/9] Guard bvec iteration logic v3
Date: Tue,  4 Apr 2017 22:56:39 +0400	[thread overview]
Message-ID: <1491332201-26926-8-git-send-email-dmonakhov@openvz.org> (raw)
In-Reply-To: <1491332201-26926-1-git-send-email-dmonakhov@openvz.org>

Currently if some one try to advance bvec beyond it's size we simply
dump WARN_ONCE and continue to iterate beyond bvec array boundaries.
This simply means that we endup dereferencing/corrupting random memory
region.

Sane reaction would be to propagate error back to calling context
But bvec_iter_advance's calling context is not always good for error
handling. For safity reason let truncate iterator size to zero which
will break external iteration loop which prevent us from unpredictable
memory range corruption. And even it caller ignores an error, it will
corrupt it's own bvecs, not others.

This patch does:
- Return error back to caller with hope that it will react on this
- Truncate iterator size

Code was added long time ago here 4550dd6c, luckily no one hit it
in real life :)

changes since V1:
 - Replace  BUG_ON with error logic.

Signed-off-by: Dmitry Monakhov <dmonakhov@openvz.org>
---
 drivers/nvdimm/blk.c |  4 +++-
 drivers/nvdimm/btt.c |  4 +++-
 include/linux/bio.h  |  8 ++++++--
 include/linux/bvec.h | 11 ++++++++---
 4 files changed, 20 insertions(+), 7 deletions(-)

diff --git a/drivers/nvdimm/blk.c b/drivers/nvdimm/blk.c
index 0b49336..c82331b 100644
--- a/drivers/nvdimm/blk.c
+++ b/drivers/nvdimm/blk.c
@@ -106,7 +106,9 @@ static int nd_blk_rw_integrity(struct nd_namespace_blk *nsblk,
 
 		len -= cur_len;
 		dev_offset += cur_len;
-		bvec_iter_advance(bip->bip_vec, &bip->bip_iter, cur_len);
+		err = bvec_iter_advance(bip->bip_vec, &bip->bip_iter, cur_len);
+		if (err)
+			return err;
 	}
 
 	return err;
diff --git a/drivers/nvdimm/btt.c b/drivers/nvdimm/btt.c
index 3d7a9fe..5a68681 100644
--- a/drivers/nvdimm/btt.c
+++ b/drivers/nvdimm/btt.c
@@ -942,7 +942,9 @@ static int btt_rw_integrity(struct btt *btt, struct bio_integrity_payload *bip,
 
 		len -= cur_len;
 		meta_nsoff += cur_len;
-		bvec_iter_advance(bip->bip_vec, &bip->bip_iter, cur_len);
+		ret = bvec_iter_advance(bip->bip_vec, &bip->bip_iter, cur_len);
+		if (ret)
+			return ret;
 	}
 
 	return ret;
diff --git a/include/linux/bio.h b/include/linux/bio.h
index 65445c0..12b7fcd 100644
--- a/include/linux/bio.h
+++ b/include/linux/bio.h
@@ -168,8 +168,12 @@ static inline void bio_advance_iter(struct bio *bio, struct bvec_iter *iter,
 
 	if (bio_no_advance_iter(bio))
 		iter->bi_size -= bytes;
-	else
-		bvec_iter_advance(bio->bi_io_vec, iter, bytes);
+	else {
+		int err;
+		err = bvec_iter_advance(bio->bi_io_vec, iter, bytes);
+		if (unlikely(err))
+			bio->bi_error = err;
+	}
 }
 
 #define __bio_for_each_segment(bvl, bio, iter, start)			\
diff --git a/include/linux/bvec.h b/include/linux/bvec.h
index 89b65b8..984a7a8 100644
--- a/include/linux/bvec.h
+++ b/include/linux/bvec.h
@@ -22,6 +22,7 @@
 
 #include <linux/kernel.h>
 #include <linux/bug.h>
+#include <linux/errno.h>
 
 /*
  * was unsigned short, but we might as well be ready for > 64kB I/O pages
@@ -66,12 +67,15 @@ struct bvec_iter {
 	.bv_offset	= bvec_iter_offset((bvec), (iter)),	\
 })
 
-static inline void bvec_iter_advance(const struct bio_vec *bv,
+static inline int bvec_iter_advance(const struct bio_vec *bv,
 				     struct bvec_iter *iter,
 				     unsigned bytes)
 {
-	WARN_ONCE(bytes > iter->bi_size,
-		  "Attempted to advance past end of bvec iter\n");
+	if (WARN_ONCE(bytes > iter->bi_size,
+		     "Attempted to advance past end of bvec iter\n")) {
+		iter->bi_size = 0;
+		return -EINVAL;
+	}
 
 	while (bytes) {
 		unsigned iter_len = bvec_iter_len(bv, *iter);
@@ -86,6 +90,7 @@ static inline void bvec_iter_advance(const struct bio_vec *bv,
 			iter->bi_idx++;
 		}
 	}
+	return 0;
 }
 
 #define for_each_bvec(bvl, bio_vec, iter, start)			\
-- 
2.9.3

  parent reply	other threads:[~2017-04-04 18:57 UTC|newest]

Thread overview: 37+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2017-04-04 18:56 [PATCH 0/9] block: T10/DIF Fixes and cleanups v3 Dmitry Monakhov
2017-04-04 18:56 ` [PATCH 1/9] bio-integrity: Do not allocate integrity context for bio w/o data Dmitry Monakhov
2017-04-05  6:32   ` Hannes Reinecke
2017-04-20  2:34   ` Martin K. Petersen
2017-04-04 18:56 ` [PATCH 2/9] bio-integrity: bio_trim should truncate integrity vector accordingly Dmitry Monakhov
2017-04-05  6:32   ` Hannes Reinecke
2017-04-20  2:34   ` Martin K. Petersen
2017-04-04 18:56 ` [PATCH 3/9] bio-integrity: bio_integrity_advance must update integrity seed Dmitry Monakhov
2017-04-05  6:34   ` Hannes Reinecke
2017-04-06 11:35   ` Christoph Hellwig
2017-04-20  2:36   ` Martin K. Petersen
2017-05-03 16:06     ` Dmitry Monakhov
2017-05-03 16:10       ` Martin K. Petersen
2017-04-04 18:56 ` [PATCH 4/9] bio-integrity: fix interface for bio_integrity_trim v2 Dmitry Monakhov
2017-04-05  6:36   ` Hannes Reinecke
2017-04-06 11:36   ` Christoph Hellwig
2017-04-20  2:38   ` Martin K. Petersen
2017-04-04 18:56 ` [PATCH 5/9] bio-integrity: fold bio_integrity_enabled to bio_integrity_prep Dmitry Monakhov
2017-04-05  6:37   ` Hannes Reinecke
2017-04-06 11:43   ` Christoph Hellwig
2017-04-20  2:40   ` Martin K. Petersen
2017-04-04 18:56 ` [PATCH 6/9] T10: Move opencoded contants to common header Dmitry Monakhov
2017-04-05  6:37   ` Hannes Reinecke
2017-04-06 11:44   ` Christoph Hellwig
2017-04-20  2:44   ` Martin K. Petersen
2017-04-04 18:56 ` Dmitry Monakhov [this message]
2017-04-05  6:39   ` [PATCH 7/9] Guard bvec iteration logic v3 Hannes Reinecke
2017-04-06 11:46   ` Christoph Hellwig
2017-04-04 18:56 ` [PATCH 8/9] bio: add bvec_iter rewind API Dmitry Monakhov
2017-04-05  6:39   ` Hannes Reinecke
2017-04-06 11:49   ` Christoph Hellwig
2017-04-20  2:51   ` Martin K. Petersen
2017-04-04 18:56 ` [PATCH 9/9] bio-integrity: Restore original iterator on verify stage Dmitry Monakhov
2017-04-05  6:41   ` Hannes Reinecke
2017-04-06 11:49   ` Christoph Hellwig
2017-05-02  7:31 ` [PATCH 0/9] block: T10/DIF Fixes and cleanups v3 Christoph Hellwig
2017-05-10 15:28   ` Dmitry Monakhov

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1491332201-26926-8-git-send-email-dmonakhov@openvz.org \
    --to=dmonakhov@openvz.org \
    --cc=linux-block@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=martin.petersen@oracle.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).