From: Theodore Ts'o Date: Wed, 10 Feb 2010 23:20:58 +0000 (-0500) Subject: Merge branch 'maint' into next X-Git-Tag: v1.42-WIP-0702~114 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=cc84d866e2f29d92b5a732fead4df2dd9f814f2b;p=thirdparty%2Fe2fsprogs.git Merge branch 'maint' into next Conflicts: e2fsck/pass1.c --- cc84d866e2f29d92b5a732fead4df2dd9f814f2b diff --cc e2fsck/pass1.c index ed03af309,695abe4c4..fb04841b1 --- a/e2fsck/pass1.c +++ b/e2fsck/pass1.c @@@ -411,19 -420,53 +420,53 @@@ static void check_is_really_dir(e2fsck_ LINUX_S_ISLNK(inode->i_mode) || inode->i_block[0] == 0) return; - for (i=0; i < EXT2_N_BLOCKS; i++) { - blk = inode->i_block[i]; - if (!blk) - continue; - if (i >= 4) - not_device++; - - if (blk < ctx->fs->super->s_first_data_block || - blk >= ext2fs_blocks_count(ctx->fs->super) || - ext2fs_fast_test_block_bitmap2(ctx->block_found_map, blk)) - return; /* Invalid block, can't be dir */ + /* + * Check the block numbers in the i_block array for validity: + * zero blocks are skipped (but the first one cannot be zero - + * see above), other blocks are checked against the first and + * max data blocks (from the the superblock) and against the + * block bitmap. Any invalid block found means this cannot be + * a directory. + * + * If there are non-zero blocks past the fourth entry, then + * this cannot be a device file: we remember that for the next + * check. + * + * For extent mapped files, we don't do any sanity checking: + * just try to get the phys block of logical block 0 and run + * with it. + */ + + extent_fs = (ctx->fs->super->s_feature_incompat & EXT3_FEATURE_INCOMPAT_EXTENTS); + if (extent_fs && (inode->i_flags & EXT4_EXTENTS_FL)) { + /* extent mapped */ + if (ext2fs_bmap(ctx->fs, pctx->ino, inode, 0, 0, 0, + &blk)) + return; + /* device files are never extent mapped */ + not_device++; + } else { + for (i=0; i < EXT2_N_BLOCKS; i++) { + blk = inode->i_block[i]; + if (!blk) + continue; + if (i >= 4) + not_device++; + + if (blk < ctx->fs->super->s_first_data_block || - blk >= ctx->fs->super->s_blocks_count || - ext2fs_fast_test_block_bitmap(ctx->block_found_map, - blk)) ++ blk >= ext2fs_blocks_count(ctx->fs->super) || ++ ext2fs_fast_test_block_bitmap2(ctx->block_found_map, ++ blk)) + return; /* Invalid block, can't be dir */ + } + blk = inode->i_block[0]; } + /* + * If the mode says this is a device file and the i_links_count field + * is sane and we have not ruled it out as a device file previously, + * we declare it a device file, not a directory. + */ if ((LINUX_S_ISCHR(inode->i_mode) || LINUX_S_ISBLK(inode->i_mode)) && (inode->i_links_count == 1) && !not_device) return; diff --cc resize/resize2fs.c index 19844429b,346fd5399..818b7b7b1 --- a/resize/resize2fs.c +++ b/resize/resize2fs.c @@@ -1815,14 -1814,17 +1815,16 @@@ static errcode_t ext2fs_calculate_summa } count++; if ((count == fs->super->s_blocks_per_group) || - (blk == fs->super->s_blocks_count-1)) { - fs->group_desc[group].bg_free_blocks_count = - group_free; + (blk == ext2fs_blocks_count(fs->super)-1)) { + ext2fs_bg_free_blocks_count_set(fs, group, group_free); ext2fs_group_desc_csum_set(fs, group); group++; + if (group >= fs->group_desc_count) + break; count = 0; group_free = 0; - uninit = (fs->group_desc[group].bg_flags & - EXT2_BG_BLOCK_UNINIT); + uninit = (ext2fs_bg_flags_test(fs, group, EXT2_BG_BLOCK_UNINIT) + ); ext2fs_super_and_bgd_loc(fs, group, &super_blk, &old_desc_blk, &new_desc_blk, 0); @@@ -1855,12 -1857,16 +1857,14 @@@ count++; if ((count == fs->super->s_inodes_per_group) || (ino == fs->super->s_inodes_count)) { - fs->group_desc[group].bg_free_inodes_count = - group_free; + ext2fs_bg_free_inodes_count_set(fs, group, group_free); ext2fs_group_desc_csum_set(fs, group); group++; + if (group >= fs->group_desc_count) + break; count = 0; group_free = 0; - uninit = (fs->group_desc[group].bg_flags & - EXT2_BG_INODE_UNINIT); + uninit = ext2fs_bg_flags_test(fs, group, EXT2_BG_INODE_UNINIT); } } fs->super->s_free_inodes_count = total_free;