1cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)/*
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * alloc_sb.c --- Allocate the superblock and block group descriptors for a
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * newly initialized filesystem.  Used by mke2fs when initializing a filesystem
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
5116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch * Copyright (C) 1994, 1995, 1996, 2003 Theodore Ts'o.
6116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch *
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * %Begin-Header%
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * This file may be redistributed under the terms of the GNU Library
9ca12bfac764ba476d6cd062bf1dde12cc64c3f40Ben Murdoch * General Public License, version 2.
10868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) * %End-Header%
11868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) */
12868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)
13868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include <stdio.h>
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <string.h>
15f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#if HAVE_UNISTD_H
16f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include <unistd.h>
17f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#endif
18f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include <fcntl.h>
19f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include <time.h>
20f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#if HAVE_SYS_STAT_H
21f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include <sys/stat.h>
22116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#endif
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if HAVE_SYS_TYPES_H
24cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)#include <sys/types.h>
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ext2_fs.h"
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ext2fs.h"
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/*
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * This function reserves the superblock and block group descriptors
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * for a given block group.  It currently returns the number of free
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * blocks assuming that inode table and allocation bitmaps will be in
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * the group.  This is not necessarily the case when the flex_bg
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * feature is enabled, so callers should take care!  It was only
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * really intended for use by mke2fs, and even there it's not that
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * useful.  In the future, when we redo this function for 64-bit block
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * numbers, we should probably return the number of blocks used by the
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * super block and group descriptors instead.
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * See also the comment for ext2fs_super_and_bgd_loc()
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int ext2fs_reserve_super_and_bgd(ext2_filsys fs,
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)				 dgrp_t group,
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)				 ext2fs_block_bitmap bmap)
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	blk64_t	super_blk, old_desc_blk, new_desc_blk;
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	blk_t	used_blks;
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	int	old_desc_blocks, num_blocks;
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	ext2fs_super_and_bgd_loc2(fs, group, &super_blk,
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)				  &old_desc_blk, &new_desc_blk, &used_blks);
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	if (fs->super->s_feature_incompat & EXT2_FEATURE_INCOMPAT_META_BG)
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		old_desc_blocks = fs->super->s_first_meta_bg;
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	else
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		old_desc_blocks =
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)			fs->desc_blocks + fs->super->s_reserved_gdt_blocks;
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	if (super_blk || (group == 0))
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		ext2fs_mark_block_bitmap2(bmap, super_blk);
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	if ((group == 0) && (fs->blocksize == 1024) &&
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    EXT2FS_CLUSTER_RATIO(fs) > 1)
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		ext2fs_mark_block_bitmap2(bmap, 0);
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
66f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)	if (old_desc_blk) {
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		if (fs->super->s_reserved_gdt_blocks && fs->block_map == bmap)
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)			ext2fs_bg_flags_clear(fs, group, EXT2_BG_BLOCK_UNINIT);
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		num_blocks = old_desc_blocks;
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		if (old_desc_blk + num_blocks >= ext2fs_blocks_count(fs->super))
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)			num_blocks = ext2fs_blocks_count(fs->super) -
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)				old_desc_blk;
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		ext2fs_mark_block_bitmap_range2(bmap, old_desc_blk, num_blocks);
745d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)	}
755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)	if (new_desc_blk)
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		ext2fs_mark_block_bitmap2(bmap, new_desc_blk);
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	num_blocks = ext2fs_group_blocks_count(fs, group);
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	num_blocks -= 2 + fs->inode_blocks_per_group + used_blks;
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	return num_blocks  ;
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)