From d7f1b2f9abde75b88e69490d619857c82e7e3517 Mon Sep 17 00:00:00 2001 From: Tomer Barletz Date: Tue, 26 Jun 2012 14:46:41 -0700 Subject: mtd-utils: Check mtdoffset is not larger than mtd.size in case of a bad block. mtdoffset is being tested against mtd.size in the outer two loops, but the third nested one does not test against it. In case of a bad block we'll try to access an out of bounds offset in the next MEMGETBADBLOCK ioctl, which will fail with EINVAL. In case mtdoffset is indeed larger than the partition size, we need to bail, since there are not enough "good" blocks to complete the write. Signed-off-by: Tomer Barletz Signed-off-by: Artem Bityutskiy --- nandwrite.c | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) (limited to 'nandwrite.c') diff --git a/nandwrite.c b/nandwrite.c index ca0c263..de8e7d2 100644 --- a/nandwrite.c +++ b/nandwrite.c @@ -385,7 +385,8 @@ int main(int argc, char * const argv[]) continue; do { - if ((ret = mtd_is_bad(&mtd, fd, offs / ebsize_aligned)) < 0) { + ret = mtd_is_bad(&mtd, fd, offs / ebsize_aligned); + if (ret < 0) { sys_errmsg("%s: MTD get bad block failed", mtd_device); goto closeall; } else if (ret == 1) { @@ -396,9 +397,15 @@ int main(int argc, char * const argv[]) offs, blockalign, blockstart); } - if (baderaseblock) + if (baderaseblock) { mtdoffset = blockstart + ebsize_aligned; + if (mtdoffset > mtd.size) { + errmsg("too many bad blocks, cannot complete request"); + goto closeall; + } + } + offs += ebsize_aligned / blockalign; } while (offs < blockstart + ebsize_aligned); -- cgit v1.2.3