useful-e2fsck-files/first-look-here/super.c
void check_resize_inode(e2fsck_t ctx)
{
	ext2_filsys fs = ctx->fs;
	struct ext2_inode inode;
	struct problem_context	pctx;
	int		i, gdt_off, ind_off;
	dgrp_t		j;
	blk_t		blk, pblk;
	blk_t		expect;	/* for resize inode, which is 32-bit only */
	__u32 		*dind_buf = 0, *ind_buf;
	errcode_t	retval;

	clear_problem_context(&pctx);

	/*
	 * If the resize inode feature isn't set, then
	 * s_reserved_gdt_blocks must be zero.
	 */
	if (!(fs->super->s_feature_compat &
	      EXT2_FEATURE_COMPAT_RESIZE_INODE)) {
		if (fs->super->s_reserved_gdt_blocks) {
			pctx.num = fs->super->s_reserved_gdt_blocks;
			if (fix_problem(ctx, PR_0_NONZERO_RESERVED_GDT_BLOCKS,
					&pctx)) {
				fs->super->s_reserved_gdt_blocks = 0;
				ext2fs_mark_super_dirty(fs);
			}
		}
	}

	/* Read the resize inode */
	pctx.ino = EXT2_RESIZE_INO;
	retval = ext2fs_read_inode(fs, EXT2_RESIZE_INO, &inode);
	if (retval) {
		if (fs->super->s_feature_compat &
		    EXT2_FEATURE_COMPAT_RESIZE_INODE)
			ctx->flags |= E2F_FLAG_RESIZE_INODE;
		return;
	}

	/*
	 * If the resize inode feature isn't set, check to make sure
	 * the resize inode is cleared; then we're done.
	 */
	if (!(fs->super->s_feature_compat &
	      EXT2_FEATURE_COMPAT_RESIZE_INODE)) {
		for (i=0; i < EXT2_N_BLOCKS; i++) {
			if (inode.i_block[i])
				break;
		}
		if ((i < EXT2_N_BLOCKS) &&
		    fix_problem(ctx, PR_0_CLEAR_RESIZE_INODE, &pctx)) {
			memset(&inode, 0, sizeof(inode));
			e2fsck_write_inode(ctx, EXT2_RESIZE_INO, &inode,
					   "clear_resize");
		}
		return;
	}

	/*
	 * The resize inode feature is enabled; check to make sure the
	 * only block in use is the double indirect block
	 */
	blk = inode.i_block[EXT2_DIND_BLOCK];
	for (i=0; i < EXT2_N_BLOCKS; i++) {
		if (i != EXT2_DIND_BLOCK && inode.i_block[i])
			break;
	}
	if ((i < EXT2_N_BLOCKS) || !blk || !inode.i_links_count ||
	    !(inode.i_mode & LINUX_S_IFREG) ||
	    (blk < fs->super->s_first_data_block ||
	     blk >= ext2fs_blocks_count(fs->super))) {
	resize_inode_invalid:
		if (fix_problem(ctx, PR_0_RESIZE_INODE_INVALID, &pctx)) {
			memset(&inode, 0, sizeof(inode));
			e2fsck_write_inode(ctx, EXT2_RESIZE_INO, &inode,
					   "clear_resize");
			ctx->flags |= E2F_FLAG_RESIZE_INODE;
		}
		if (!(ctx->options & E2F_OPT_READONLY)) {
			fs->super->s_state &= ~EXT2_VALID_FS;
			ext2fs_mark_super_dirty(fs);
		}
		goto cleanup;
	}
	dind_buf = (__u32 *) e2fsck_allocate_memory(ctx, fs->blocksize * 2,
						    "resize dind buffer");
	ind_buf = (__u32 *) ((char *) dind_buf + fs->blocksize);

	retval = ext2fs_read_ind_block(fs, blk, dind_buf);
	if (retval)
		goto resize_inode_invalid;

	gdt_off = fs->desc_blocks;
	pblk = fs->super->s_first_data_block + 1 + fs->desc_blocks;
	if (fs->blocksize == 1024 && fs->super->s_first_data_block == 0)
		pblk++;	/* Deal with 1024 blocksize bigalloc fs */
	for (i = 0; i < fs->super->s_reserved_gdt_blocks / 4;
	     i++, gdt_off++, pblk++) {
		gdt_off %= fs->blocksize/4;
		if (dind_buf[gdt_off] != pblk)
			goto resize_inode_invalid;
		retval = ext2fs_read_ind_block(fs, pblk, ind_buf);
		if (retval)
			goto resize_inode_invalid;
		ind_off = 0;
		for (j = 1; j < fs->group_desc_count; j++) {
			if (!ext2fs_bg_has_super(fs, j))
				continue;
			expect = pblk + EXT2_GROUPS_TO_BLOCKS(fs->super, j);
			if (ind_buf[ind_off] != expect)
				goto resize_inode_invalid;
			ind_off++;
		}
	}

cleanup:
	if (dind_buf)
		ext2fs_free_mem(&dind_buf);

 }
/*
 * Check the resize inode to make sure it is sane.  We check both for
 * the case where on-line resizing is not enabled (in which case the
 * resize inode should be cleared) as well as the case where on-line
 * resizing is enabled.
 */
Check the resize inode to make sure it is sane.  We check both for
the case where on-line resizing is not enabled (in which case the
resize inode should be cleared) as well as the case where on-line
resizing is enabled.
Check the resize inode to make sure it is sane . We check both for the case where on - line resizing is not enabled ( in which case the resize inode should be cleared ) as well as the case where on - line resizing is enabled .
void check_resize_inode(e2fsck_t ctx)
{
	ext2_filsys fs = ctx->fs;
	struct ext2_inode inode;
	struct problem_context	pctx;
	int		i, gdt_off, ind_off;
	dgrp_t		j;
	blk_t		blk, pblk;
	blk_t		expect;	
	__u32 		*dind_buf = 0, *ind_buf;
	errcode_t	retval;
	clear_problem_context(&pctx);
	if (!(fs->super->s_feature_compat &
	      EXT2_FEATURE_COMPAT_RESIZE_INODE)) {
		if (fs->super->s_reserved_gdt_blocks) {
			pctx.num = fs->super->s_reserved_gdt_blocks;
			if (fix_problem(ctx, PR_0_NONZERO_RESERVED_GDT_BLOCKS,
					&pctx)) {
				fs->super->s_reserved_gdt_blocks = 0;
				ext2fs_mark_super_dirty(fs);
			}
		}
	}
	pctx.ino = EXT2_RESIZE_INO;
	retval = ext2fs_read_inode(fs, EXT2_RESIZE_INO, &inode);
	if (retval) {
		if (fs->super->s_feature_compat &
		    EXT2_FEATURE_COMPAT_RESIZE_INODE)
			ctx->flags |= E2F_FLAG_RESIZE_INODE;
		return;
	}
	if (!(fs->super->s_feature_compat &
	      EXT2_FEATURE_COMPAT_RESIZE_INODE)) {
		for (i=0; i < EXT2_N_BLOCKS; i++) {
			if (inode.i_block[i])
				break;
		}
		if ((i < EXT2_N_BLOCKS) &&
		    fix_problem(ctx, PR_0_CLEAR_RESIZE_INODE, &pctx)) {
			memset(&inode, 0, sizeof(inode));
			e2fsck_write_inode(ctx, EXT2_RESIZE_INO, &inode,
					   "clear_resize");
		}
		return;
	}
	blk = inode.i_block[EXT2_DIND_BLOCK];
	for (i=0; i < EXT2_N_BLOCKS; i++) {
		if (i != EXT2_DIND_BLOCK && inode.i_block[i])
			break;
	}
	if ((i < EXT2_N_BLOCKS) || !blk || !inode.i_links_count ||
	    !(inode.i_mode & LINUX_S_IFREG) ||
	    (blk < fs->super->s_first_data_block ||
	     blk >= ext2fs_blocks_count(fs->super))) {
	resize_inode_invalid:
		if (fix_problem(ctx, PR_0_RESIZE_INODE_INVALID, &pctx)) {
			memset(&inode, 0, sizeof(inode));
			e2fsck_write_inode(ctx, EXT2_RESIZE_INO, &inode,
					   "clear_resize");
			ctx->flags |= E2F_FLAG_RESIZE_INODE;
		}
		if (!(ctx->options & E2F_OPT_READONLY)) {
			fs->super->s_state &= ~EXT2_VALID_FS;
			ext2fs_mark_super_dirty(fs);
		}
		goto cleanup;
	}
	dind_buf = (__u32 *) e2fsck_allocate_memory(ctx, fs->blocksize * 2,
						    "resize dind buffer");
	ind_buf = (__u32 *) ((char *) dind_buf + fs->blocksize);
	retval = ext2fs_read_ind_block(fs, blk, dind_buf);
	if (retval)
		goto resize_inode_invalid;
	gdt_off = fs->desc_blocks;
	pblk = fs->super->s_first_data_block + 1 + fs->desc_blocks;
	if (fs->blocksize == 1024 && fs->super->s_first_data_block == 0)
		pblk++;	
	for (i = 0; i < fs->super->s_reserved_gdt_blocks / 4;
	     i++, gdt_off++, pblk++) {
		gdt_off %= fs->blocksize/4;
		if (dind_buf[gdt_off] != pblk)
			goto resize_inode_invalid;
		retval = ext2fs_read_ind_block(fs, pblk, ind_buf);
		if (retval)
			goto resize_inode_invalid;
		ind_off = 0;
		for (j = 1; j < fs->group_desc_count; j++) {
			if (!ext2fs_bg_has_super(fs, j))
				continue;
			expect = pblk + EXT2_GROUPS_TO_BLOCKS(fs->super, j);
			if (ind_buf[ind_off] != expect)
				goto resize_inode_invalid;
			ind_off++;
		}
	}
cleanup:
	if (dind_buf)
		ext2fs_free_mem(&dind_buf);
 }
void check_resize_inode ( e2fsck_t ctx ) { ext2_filsys fs = ctx -> fs ; struct ext2_inode inode ; struct problem_context pctx ; int i , gdt_off , ind_off ; dgrp_t j ; blk_t blk , pblk ; blk_t expect ; __u32 * dind_buf = 0 , * ind_buf ; errcode_t retval ; clear_problem_context ( & pctx ) ; if ( ! ( fs -> super -> s_feature_compat & EXT2_FEATURE_COMPAT_RESIZE_INODE ) ) { if ( fs -> super -> s_reserved_gdt_blocks ) { pctx . num = fs -> super -> s_reserved_gdt_blocks ; if ( fix_problem ( ctx , PR_0_NONZERO_RESERVED_GDT_BLOCKS , & pctx ) ) { fs -> super -> s_reserved_gdt_blocks = 0 ; ext2fs_mark_super_dirty ( fs ) ; } } } pctx . ino = EXT2_RESIZE_INO ; retval = ext2fs_read_inode ( fs , EXT2_RESIZE_INO , & inode ) ; if ( retval ) { if ( fs -> super -> s_feature_compat & EXT2_FEATURE_COMPAT_RESIZE_INODE ) ctx -> flags |= E2F_FLAG_RESIZE_INODE ; return ; } if ( ! ( fs -> super -> s_feature_compat & EXT2_FEATURE_COMPAT_RESIZE_INODE ) ) { for ( i = 0 ; i < EXT2_N_BLOCKS ; i ++ ) { if ( inode . i_block [ i ] ) break ; } if ( ( i < EXT2_N_BLOCKS ) && fix_problem ( ctx , PR_0_CLEAR_RESIZE_INODE , & pctx ) ) { memset ( & inode , 0 , sizeof ( inode ) ) ; e2fsck_write_inode ( ctx , EXT2_RESIZE_INO , & inode , " " ) ; } return ; } blk = inode . i_block [ EXT2_DIND_BLOCK ] ; for ( i = 0 ; i < EXT2_N_BLOCKS ; i ++ ) { if ( i != EXT2_DIND_BLOCK && inode . i_block [ i ] ) break ; } if ( ( i < EXT2_N_BLOCKS ) || ! blk || ! inode . i_links_count || ! ( inode . i_mode & LINUX_S_IFREG ) || ( blk < fs -> super -> s_first_data_block || blk >= ext2fs_blocks_count ( fs -> super ) ) ) { resize_inode_invalid : if ( fix_problem ( ctx , PR_0_RESIZE_INODE_INVALID , & pctx ) ) { memset ( & inode , 0 , sizeof ( inode ) ) ; e2fsck_write_inode ( ctx , EXT2_RESIZE_INO , & inode , " " ) ; ctx -> flags |= E2F_FLAG_RESIZE_INODE ; } if ( ! ( ctx -> options & E2F_OPT_READONLY ) ) { fs -> super -> s_state &= ~ EXT2_VALID_FS ; ext2fs_mark_super_dirty ( fs ) ; } goto cleanup ; } dind_buf = ( __u32 * ) e2fsck_allocate_memory ( ctx , fs -> blocksize * 2 , " " ) ; ind_buf = ( __u32 * ) ( ( char * ) dind_buf + fs -> blocksize ) ; retval = ext2fs_read_ind_block ( fs , blk , dind_buf ) ; if ( retval ) goto resize_inode_invalid ; gdt_off = fs -> desc_blocks ; pblk = fs -> super -> s_first_data_block + 1 + fs -> desc_blocks ; if ( fs -> blocksize == 1024 && fs -> super -> s_first_data_block == 0 ) pblk ++ ; for ( i = 0 ; i < fs -> super -> s_reserved_gdt_blocks / 4 ; i ++ , gdt_off ++ , pblk ++ ) { gdt_off %= fs -> blocksize / 4 ; if ( dind_buf [ gdt_off ] != pblk ) goto resize_inode_invalid ; retval = ext2fs_read_ind_block ( fs , pblk , ind_buf ) ; if ( retval ) goto resize_inode_invalid ; ind_off = 0 ; for ( j = 1 ; j < fs -> group_desc_count ; j ++ ) { if ( ! ext2fs_bg_has_super ( fs , j ) ) continue ; expect = pblk + EXT2_GROUPS_TO_BLOCKS ( fs -> super , j ) ; if ( ind_buf [ ind_off ] != expect ) goto resize_inode_invalid ; ind_off ++ ; } } cleanup : if ( dind_buf ) ext2fs_free_mem ( & dind_buf ) ; }
Check the resize inode to make sure it is sane.
Check the resize inode to make sure it is sane .
/* for resize inode, which is 32-bit only */ /*
	 * If the resize inode feature isn't set, then
	 * s_reserved_gdt_blocks must be zero.
	 */ /* Read the resize inode */ /*
	 * If the resize inode feature isn't set, check to make sure
	 * the resize inode is cleared; then we're done.
	 */ /*
	 * The resize inode feature is enabled; check to make sure the
	 * only block in use is the double indirect block
	 */ /* Deal with 1024 blocksize bigalloc fs */