Do sanity checking of the number of blocks and inodes in a group for

8192-byte and 16384-byte blocksize filesystems.

Change the default bytes-per-inode ratio of a new filesystem to be at most
one inode per block for large blocksizes.
bitmap-optimize
Andreas Dilger 2002-06-10 11:05:56 -06:00
parent 7da78ff17d
commit b21bf26778
17 changed files with 110 additions and 30 deletions

View File

@ -1,3 +1,10 @@
2002-05-22 Andreas Dilger <adilger@clusterfs.com>
* super.c (check_superblock): Check that the number of inodes and
blocks in a group is less than 2^16, so that the free inode
and block counts for a group fit into the group descriptor
table fields. Any more than that would need a COMPAT flag.
2002-05-22 Theodore Ts'o <tytso@mit.edu>
* pass1.c (check_ext_attr): Update to support the V2 Bestbits EA

View File

@ -308,13 +308,20 @@ void check_super_block(e2fsck_t ctx)
blk_t first_block, last_block;
struct ext2_super_block *sb = fs->super;
blk_t blocks_per_group = fs->super->s_blocks_per_group;
blk_t bpg_max;
int inodes_per_block;
int ipg_max;
dgrp_t i;
blk_t should_be;
struct problem_context pctx;
inodes_per_block = (EXT2_BLOCK_SIZE(fs->super) /
EXT2_INODE_SIZE(fs->super));
inodes_per_block = EXT2_INODES_PER_BLOCK(fs->super);
ipg_max = inodes_per_block * (blocks_per_group - 4);
if (ipg_max > EXT2_MAX_INODES_PER_GROUP(sb))
ipg_max = EXT2_MAX_INODES_PER_GROUP(sb);
bpg_max = 8 * EXT2_BLOCK_SIZE(sb);
if (bpg_max > EXT2_MAX_BLOCKS_PER_GROUP(sb))
bpg_max = EXT2_MAX_BLOCKS_PER_GROUP(sb);
ctx->invalid_inode_bitmap_flag = (int *) e2fsck_allocate_memory(ctx,
sizeof(int) * fs->group_desc_count, "invalid_inode_bitmap");
@ -322,7 +329,7 @@ void check_super_block(e2fsck_t ctx)
sizeof(int) * fs->group_desc_count, "invalid_block_bitmap");
ctx->invalid_inode_table_flag = (int *) e2fsck_allocate_memory(ctx,
sizeof(int) * fs->group_desc_count, "invalid_inode_table");
clear_problem_context(&pctx);
/*
@ -341,12 +348,11 @@ void check_super_block(e2fsck_t ctx)
MIN_CHECK | MAX_CHECK, 0, sb->s_log_block_size);
check_super_value(ctx, "frags_per_group", sb->s_frags_per_group,
MIN_CHECK | MAX_CHECK, sb->s_blocks_per_group,
8 * EXT2_BLOCK_SIZE(sb));
bpg_max);
check_super_value(ctx, "blocks_per_group", sb->s_blocks_per_group,
MIN_CHECK | MAX_CHECK, 8, 8 * EXT2_BLOCK_SIZE(sb));
MIN_CHECK | MAX_CHECK, 8, bpg_max);
check_super_value(ctx, "inodes_per_group", sb->s_inodes_per_group,
MIN_CHECK | MAX_CHECK, inodes_per_block,
inodes_per_block * (blocks_per_group-4));
MIN_CHECK | MAX_CHECK, inodes_per_block, ipg_max);
check_super_value(ctx, "r_blocks_count", sb->s_r_blocks_count,
MAX_CHECK, 0, sb->s_blocks_count / 4);

View File

@ -1,3 +1,16 @@
2002-06-09 Andreas Dilger <adilger@clusterfs.com>
* ext2_fs.h: Add macros for maximum block/inode counts:
EXT2_INODES_PER_BLOCK, EXT2_MAX_BLOCKS_PER_GROUP,
and EXT2_MAX_INODES_PER_GROUP.
* openfs.c (ext2fs_open): Check that the number of blocks in a group
is less than 2^16, otherwise we need an INCOMPAT flag (not
in existence yet, if ever) to open such a filesystem.
* initialize.c (ext2fs_initialize): Limit the number of blocks and
inodes in a group to less than 2^16.
2002-06-09 Andreas Dilger <adilger@clusterfs.com>
* ext2_fs.h: Further minor cleanups of the header. Consolidate

View File

@ -181,15 +181,17 @@ struct ext2_dx_countlimit {
/*
* Macro-instructions used to manage group descriptors
*/
#define EXT2_BLOCKS_PER_GROUP(s) (EXT2_SB(s)->s_blocks_per_group)
#define EXT2_INODES_PER_GROUP(s) (EXT2_SB(s)->s_inodes_per_group)
#define EXT2_INODES_PER_BLOCK(s) (EXT2_BLOCK_SIZE(s)/EXT2_INODE_SIZE(s))
/* limits imposed by 16-bit value gd_free_{blocks,inode}_count */
#define EXT2_MAX_BLOCKS_PER_GROUP(s) ((1 << 16) - 8)
#define EXT2_MAX_INODES_PER_GROUP(s) ((1 << 16) - EXT2_INODES_PER_BLOCK(s))
#ifdef __KERNEL__
# define EXT2_BLOCKS_PER_GROUP(s) (EXT2_SB(s)->s_blocks_per_group)
# define EXT2_DESC_PER_BLOCK(s) (EXT2_SB(s)->s_desc_per_block)
# define EXT2_INODES_PER_GROUP(s) (EXT2_SB(s)->s_inodes_per_group)
# define EXT2_DESC_PER_BLOCK_BITS(s) (EXT2_SB(s)->s_desc_per_block_bits)
#define EXT2_DESC_PER_BLOCK(s) (EXT2_SB(s)->s_desc_per_block)
#define EXT2_DESC_PER_BLOCK_BITS(s) (EXT2_SB(s)->s_desc_per_block_bits)
#else
# define EXT2_BLOCKS_PER_GROUP(s) ((s)->s_blocks_per_group)
# define EXT2_DESC_PER_BLOCK(s) (EXT2_BLOCK_SIZE(s) / sizeof (struct ext2_group_desc))
# define EXT2_INODES_PER_GROUP(s) ((s)->s_inodes_per_group)
#define EXT2_DESC_PER_BLOCK(s) (EXT2_BLOCK_SIZE(s) / sizeof (struct ext2_group_desc))
#endif
/*

View File

@ -63,6 +63,7 @@ errcode_t ext2fs_initialize(const char *name, int flags,
int rem;
int overhead = 0;
blk_t group_block;
int ipg;
int i, j;
blk_t numblocks;
char *buf;
@ -131,9 +132,11 @@ errcode_t ext2fs_initialize(const char *name, int flags,
fs->blocksize = EXT2_BLOCK_SIZE(super);
fs->fragsize = EXT2_FRAG_SIZE(super);
frags_per_block = fs->blocksize / fs->fragsize;
/* default: (fs->blocksize*8) blocks/group */
set_field(s_blocks_per_group, fs->blocksize*8);
/* default: (fs->blocksize*8) blocks/group, up to 2^16 (GDT limit) */
set_field(s_blocks_per_group, fs->blocksize * 8);
if (super->s_blocks_per_group > EXT2_MAX_BLOCKS_PER_GROUP(super))
super->s_blocks_per_group = EXT2_MAX_BLOCKS_PER_GROUP(super);
super->s_frags_per_group = super->s_blocks_per_group * frags_per_block;
super->s_blocks_count = param->s_blocks_count;
@ -180,14 +183,20 @@ retry:
* There should be at least as many inodes as the user
* requested. Figure out how many inodes per group that
* should be. But make sure that we don't allocate more than
* one bitmap's worth of inodes
* one bitmap's worth of inodes each group.
*/
super->s_inodes_per_group = (super->s_inodes_count +
fs->group_desc_count - 1) /
fs->group_desc_count;
if (super->s_inodes_per_group > fs->blocksize*8)
super->s_inodes_per_group = fs->blocksize*8;
ipg = (super->s_inodes_count + fs->group_desc_count - 1) /
fs->group_desc_count;
if (ipg > fs->blocksize * 8)
ipg = fs->blocksize * 8;
if (ipg > EXT2_MAX_INODES_PER_GROUP(super))
ipg = EXT2_MAX_INODES_PER_GROUP(super);
super->s_inodes_per_group = ipg;
if (super->s_inodes_count > ipg * fs->group_desc_count)
super->s_inodes_count = ipg * fs->group_desc_count;
/*
* Make sure the number of inodes per group completely fills
* the inode table blocks in the descriptor. If not, add some

View File

@ -43,7 +43,7 @@ errcode_t ext2fs_open(const char *name, int flags, int superblock,
{
ext2_filsys fs;
errcode_t retval;
int i, j, groups_per_block;
int i, j, groups_per_block, blocks_per_group;
blk_t group_block;
char *dest;
struct ext2_group_desc *gdp;
@ -196,14 +196,16 @@ errcode_t ext2fs_open(const char *name, int flags, int superblock,
/*
* Read group descriptors
*/
if ((EXT2_BLOCKS_PER_GROUP(fs->super)) == 0) {
blocks_per_group = EXT2_BLOCKS_PER_GROUP(fs->super);
if (blocks_per_group == 0 ||
blocks_per_group > EXT2_MAX_BLOCKS_PER_GROUP(fs->super) ||
fs->inode_blocks_per_group > EXT2_MAX_INODES_PER_GROUP(fs->super)) {
retval = EXT2_ET_CORRUPT_SUPERBLOCK;
goto cleanup;
}
fs->group_desc_count = (fs->super->s_blocks_count -
fs->super->s_first_data_block +
EXT2_BLOCKS_PER_GROUP(fs->super) - 1)
/ EXT2_BLOCKS_PER_GROUP(fs->super);
blocks_per_group - 1) / blocks_per_group;
fs->desc_blocks = (fs->group_desc_count +
EXT2_DESC_PER_BLOCK(fs->super) - 1)
/ EXT2_DESC_PER_BLOCK(fs->super);

View File

@ -1,3 +1,8 @@
2002-05-22 Andreas Dilger <adilger@clusterfs.com>
* mke2fs.c (set_fs_defaults): make the default inode ratio at most
one inode per block for large blocksizes.
2002-05-17 Theodore Ts'o <tytso@mit.edu>
* mke2fs.c (PRS): Determine the page size using sysconf() at

View File

@ -166,7 +166,8 @@ static void set_fs_defaults(const char *fs_type,
(megs > p->size))
continue;
if (ratio == 0)
*inode_ratio = p->inode_ratio;
*inode_ratio = p->inode_ratio < blocksize ?
blocksize : p->inode_ratio;
if (blocksize == 0) {
if (p->blocksize == DEF_MAX_BLOCKSIZE)
p->blocksize = sys_page_size;

View File

@ -1,3 +1,8 @@
2002-06-09 Andreas Dilger <adilger@clusterfs.com>
* f_8192_block, f_16384_block: Basic tests of 8192-byte block
and 16384-byte blocksize filesystems.
2002-05-21 Theodore Ts'o <tytso@mit.edu>
* f_badsymlinks: Check for symlink too big error message.

View File

@ -0,0 +1,7 @@
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
test_filesys: 11/2048 files (0.0% non-contiguous), 39/1024 blocks
Exit status is 0

View File

@ -0,0 +1,7 @@
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
test_filesys: 11/2048 files (0.0% non-contiguous), 39/1024 blocks
Exit status is 0

Binary file not shown.

1
tests/f_16384_block/name Normal file
View File

@ -0,0 +1 @@
16384 byte blocksize

View File

@ -0,0 +1,7 @@
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
test_filesys: 11/2048 files (0.0% non-contiguous), 39/1024 blocks
Exit status is 0

View File

@ -0,0 +1,7 @@
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
test_filesys: 11/2048 files (0.0% non-contiguous), 39/1024 blocks
Exit status is 0

BIN
tests/f_8192_block/image.gz Normal file

Binary file not shown.

1
tests/f_8192_block/name Normal file
View File

@ -0,0 +1 @@
8192 byte blocksize