*/
errcode_t ext2fs_check_desc(ext2_filsys fs)
{
+ ext2fs_block_bitmap bmap;
+ errcode_t retval;
dgrp_t i;
blk_t first_block = fs->super->s_first_data_block;
blk_t last_block = fs->super->s_blocks_count-1;
+ blk_t blk, b;
+ int j;
EXT2_CHECK_MAGIC(fs, EXT2_ET_MAGIC_EXT2FS_FILSYS);
+ retval = ext2fs_allocate_block_bitmap(fs, "check_desc map", &bmap);
+ if (retval)
+ return retval;
+
+ for (i = 0; i < fs->group_desc_count; i++)
+ ext2fs_reserve_super_and_bgd(fs, i, bmap);
+
for (i = 0; i < fs->group_desc_count; i++) {
if (!EXT2_HAS_INCOMPAT_FEATURE(fs->super,
EXT4_FEATURE_INCOMPAT_FLEX_BG)) {
first_block = ext2fs_group_first_block(fs, i);
last_block = ext2fs_group_last_block(fs, i);
+ if (i == (fs->group_desc_count - 1))
+ last_block = fs->super->s_blocks_count-1;
}
/*
- * Check to make sure block bitmap for group is
- * located within the group.
+ * Check to make sure the block bitmap for group is sane
*/
- if (fs->group_desc[i].bg_block_bitmap < first_block ||
- fs->group_desc[i].bg_block_bitmap > last_block)
- return EXT2_ET_GDESC_BAD_BLOCK_MAP;
+ blk = fs->group_desc[i].bg_block_bitmap;
+ if (blk < first_block || blk > last_block ||
+ ext2fs_test_block_bitmap(bmap, blk)) {
+ retval = EXT2_ET_GDESC_BAD_BLOCK_MAP;
+ goto errout;
+ }
+ ext2fs_mark_block_bitmap(bmap, blk);
+
/*
- * Check to make sure inode bitmap for group is
- * located within the group
+ * Check to make sure the inode bitmap for group is sane
*/
- if (fs->group_desc[i].bg_inode_bitmap < first_block ||
- fs->group_desc[i].bg_inode_bitmap > last_block)
- return EXT2_ET_GDESC_BAD_INODE_MAP;
+ blk = fs->group_desc[i].bg_inode_bitmap;
+ if (blk < first_block || blk > last_block ||
+ ext2fs_test_block_bitmap(bmap, blk)) {
+ retval = EXT2_ET_GDESC_BAD_INODE_MAP;
+ goto errout;
+ }
+ ext2fs_mark_block_bitmap(bmap, blk);
+
/*
- * Check to make sure inode table for group is located
- * within the group
+ * Check to make sure the inode table for group is sane
*/
- if (fs->group_desc[i].bg_inode_table < first_block ||
- ((fs->group_desc[i].bg_inode_table +
- fs->inode_blocks_per_group - 1) > last_block))
- return EXT2_ET_GDESC_BAD_INODE_TABLE;
+ blk = fs->group_desc[i].bg_inode_table;
+ if (blk < first_block ||
+ ((blk + fs->inode_blocks_per_group - 1) > last_block)) {
+ retval = EXT2_ET_GDESC_BAD_INODE_TABLE;
+ goto errout;
+ }
+ for (j = 0, b = blk; j < fs->inode_blocks_per_group;
+ j++, b++) {
+ if (ext2fs_test_block_bitmap(bmap, b)) {
+ retval = EXT2_ET_GDESC_BAD_INODE_TABLE;
+ goto errout;
+ }
+ ext2fs_mark_block_bitmap(bmap, b);
+ }
}
- return 0;
+errout:
+ ext2fs_free_block_bitmap(bmap);
+ return retval;
}
debugfs -R ''set_super_value reserved_gdt_blocks 15679'' -w ./test.img
Exit status is 0
-Corruption found in superblock. (reserved_gdt_blocks = 15679).
-
-The superblock could not be read or does not describe a correct ext2
-filesystem. If the device is valid and it really contains an ext2
-filesystem (and not swap or ufs or something else), then the superblock
-is corrupt, and you might try running e2fsck with an alternate superblock:
- e2fsck -b 1025 <device>
+../e2fsck/e2fsck: Group descriptors look bad... trying backup blocks...
+Pass 1: Checking inodes, blocks, and sizes
+Pass 2: Checking directory structure
+Pass 3: Checking directory connectivity
+Pass 4: Checking reference counts
+Pass 5: Checking group summary information
-Exit status is 8
+test_filesys: ***** FILE SYSTEM WAS MODIFIED *****
+test_filesys: 11/4096 files (0.0% non-contiguous), 2107/16384 blocks
+Exit status is 1
-----------------------------------------------
debugfs -R ''set_super_value reserved_gdt_blocks 32'' -w ./test.img