ext4: Avoid out-of-bounds access of block bitmap
authorStefan Brüns <stefan.bruens@rwth-aachen.de>
Tue, 6 Sep 2016 02:36:50 +0000 (04:36 +0200)
committerTom Rini <trini@konsulko.com>
Fri, 23 Sep 2016 13:02:40 +0000 (09:02 -0400)
If the blocksize is 1024, count is initialized with 1. Incrementing count
by 8 will never match (count == fs->blksz * 8), and ptr may be
incremented beyond the buffer end if the bitmap is filled. Add the
startblock offset after the loop.

Remove the second loop, as only the first iteration will be done.

Signed-off-by: Stefan Brüns <stefan.bruens@rwth-aachen.de>
Reviewed-by: Lukasz Majewski <l.majewski@samsung.com>
fs/ext4/ext4_common.c

index db5cdb9c06c30cc97eeb9d7bafbd7190695eb73c..5e874afc70cfcdb3a9c25d05b655ee1d4ecad3d0 100644 (file)
@@ -163,18 +163,12 @@ static int _get_new_inode_no(unsigned char *buffer)
 
 static int _get_new_blk_no(unsigned char *buffer)
 {
-       unsigned char input;
-       int operand, status;
+       int operand;
        int count = 0;
-       int j = 0;
+       int i;
        unsigned char *ptr = buffer;
        struct ext_filesystem *fs = get_fs();
 
-       if (fs->blksz != 1024)
-               count = 0;
-       else
-               count = 1;
-
        while (*ptr == 255) {
                ptr++;
                count += 8;
@@ -182,21 +176,17 @@ static int _get_new_blk_no(unsigned char *buffer)
                        return -1;
        }
 
-       for (j = 0; j < fs->blksz; j++) {
-               input = *ptr;
-               int i = 0;
-               while (i <= 7) {
-                       operand = 1 << i;
-                       status = input & operand;
-                       if (status) {
-                               i++;
-                               count++;
-                       } else {
-                               *ptr |= operand;
-                               return count;
-                       }
+       if (fs->blksz == 1024)
+               count += 1;
+
+       for (i = 0; i <= 7; i++) {
+               operand = 1 << i;
+               if (*ptr & operand) {
+                       count++;
+               } else {
+                       *ptr |= operand;
+                       return count;
                }
-               ptr = ptr + 1;
        }
 
        return -1;