/*
    ext2_resize.c -- ext2 resizer
    Copyright (C) 1998-2000 Free Software Foundation, Inc.
  
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation; either version 2 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program; if not, write to the Free Software
    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA.
*/

#include <config.h>

#ifndef DISCOVER_ONLY

#include <stdio.h>
#include <stdlib.h>
#include "ext2.h"

static int ext2_add_group(struct ext2_fs *fs, blk_t groupsize)
{
	blk_t admin;
	int   group;
	blk_t groupstart;
	blk_t newgdblocks;
	int   sparse;

	if (fs->opt_verbose)
                fputs ("ext2_add_group\n", stderr);

	if (!ped_realloc ((void*) &fs->gd,
			  (fs->numgroups+1) * sizeof(struct ext2_group_desc)
			      + fs->blocksize))
		return 0;

	if (fs->opt_debug)
	{
		if (EXT2_SUPER_BLOCKS_COUNT(fs->sb) !=
		    EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb)
		    + fs->numgroups * EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb))
		{
                        fputs ("ext2_add_group: last (existing) group "
                               "isn't complete!\n", stderr);

			return 0;
		}
	}

	group = fs->numgroups;
	sparse = ext2_is_group_sparse(fs, group);
	groupstart = EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb)
		     + group * EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);

	admin = fs->adminblocks;
	if (!sparse)
		admin -= fs->gdblocks + 1;

	if (fs->opt_debug)
	{
		if (groupsize < fs->adminblocks ||
		    groupsize > EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb))
		{
			fprintf(stderr,
				"ext2_add_group: groups of %i blocks are "
				"impossible!\n", groupsize);

			return 0;
		}
	}

	newgdblocks = ped_div_round_up((fs->numgroups + 1)
					* sizeof(struct ext2_group_desc),
			      fs->blocksize);
	if (newgdblocks != fs->gdblocks)
	{
		int i;

		for (i=0;i<fs->numgroups;i++)
			if (ext2_is_group_sparse(fs, i))
			{
				blk_t start;

				start = EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb)
				      + i * EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);
				ext2_set_block_state(fs,
						start + fs->gdblocks + 1, 1, 1);
			}

		fs->gdblocks++;
		fs->adminblocks++;
		if (sparse)
			admin++;
	}

	fs->numgroups++;

	fs->sb.s_inodes_count = PED_CPU_TO_LE32(
		EXT2_SUPER_INODES_COUNT(fs->sb)
		+ EXT2_SUPER_INODES_PER_GROUP(fs->sb));
	fs->sb.s_blocks_count = PED_CPU_TO_LE32(
		EXT2_SUPER_BLOCKS_COUNT(fs->sb) + groupsize);
	fs->sb.s_free_blocks_count = PED_CPU_TO_LE32(
		EXT2_SUPER_FREE_BLOCKS_COUNT(fs->sb) + groupsize - admin);
	fs->sb.s_free_inodes_count = PED_CPU_TO_LE32(
		EXT2_SUPER_FREE_INODES_COUNT(fs->sb)
	        + EXT2_SUPER_INODES_PER_GROUP(fs->sb));
	fs->metadirty |= EXT2_META_SB;

	{
		blk_t off;
		blk_t sparseoff;

		off = groupstart;
		sparseoff = off + fs->itoffset - 2;

		if (sparse)
		{
			fs->gd[group].bg_block_bitmap
				= PED_CPU_TO_LE32(sparseoff);
			fs->gd[group].bg_inode_bitmap
				= PED_CPU_TO_LE32(sparseoff + 1);
		}
		else
		{
			fs->gd[group].bg_block_bitmap
				= PED_CPU_TO_LE32(off);
			fs->gd[group].bg_inode_bitmap
				= PED_CPU_TO_LE32(off + 1);
		}

		/* Hey, I don't know _why_ either */
		fs->gd[group].bg_inode_table = PED_CPU_TO_LE32(sparseoff + 2);
	}

	fs->gd[group].bg_free_blocks_count = PED_CPU_TO_LE16(groupsize - admin);
	fs->gd[group].bg_free_inodes_count = PED_CPU_TO_LE16(
		EXT2_SUPER_INODES_PER_GROUP(fs->sb));
	fs->gd[group].bg_used_dirs_count = 0;
	fs->metadirty |= EXT2_META_SB | EXT2_META_GD;

	{
		struct ext2_buffer_head *bh;
		blk_t i;

		bh = ext2_bcreate(fs, EXT2_GROUP_BLOCK_BITMAP(fs->gd[group]));
		if (!bh)
			return 0;

		if (sparse)
		{
			bh->data[0] |= _bitmap[0];
			for (i=1;i<=fs->gdblocks;i++)
				bh->data[i>>3] |= _bitmap[i&7];
		}

		i = EXT2_GROUP_BLOCK_BITMAP(fs->gd[group]) - groupstart;
		bh->data[i>>3] |= _bitmap[i&7];

		i = EXT2_GROUP_INODE_BITMAP(fs->gd[group]) - groupstart;
		bh->data[i>>3] |= _bitmap[i&7];

		for (i=0;i<fs->inodeblocks;i++)
		{
			blk_t j;

			j = EXT2_GROUP_INODE_TABLE(fs->gd[group])
			    - groupstart + i;
			bh->data[j>>3] |= _bitmap[j&7];
		}

		for (i=groupsize;i<EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);i++)
			bh->data[i>>3] |= _bitmap[i&7];

		ext2_brelse(bh, 0);         /* this is a block bitmap */
	}

	if (!ext2_zero_blocks(fs, EXT2_GROUP_INODE_BITMAP(fs->gd[group]), 1))
		return 0;
	if (!ext2_zero_blocks(fs, EXT2_GROUP_INODE_TABLE(fs->gd[group]),
			      fs->inodeblocks))
		return 0;

	if (fs->opt_safe)
		if (!ext2_sync(fs))
			return 0;

	return 1;
}

static int ext2_del_group(struct ext2_fs *fs)
{
	blk_t admin;
	int   group;
	blk_t groupsize;
	blk_t newgdblocks;
	int   sparse;

	if (fs->opt_verbose)
                fputs ("ext2_del_group\n", stderr);

	group = fs->numgroups - 1;
	sparse = ext2_is_group_sparse(fs, group);

	admin = fs->adminblocks;
	if (!sparse)
		admin -= fs->gdblocks + 1;

	groupsize = EXT2_SUPER_BLOCKS_COUNT(fs->sb)
		  - EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb)
		  - group * EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);

	if (EXT2_SUPER_FREE_BLOCKS_COUNT(fs->sb) < groupsize - admin)
	{
		ped_exception_throw (PED_EXCEPTION_ERROR, PED_EXCEPTION_CANCEL,
			_("File system is too full to remove a group!"));

		return 0;
	}

	if (EXT2_SUPER_FREE_INODES_COUNT(fs->sb)
		< EXT2_SUPER_INODES_PER_GROUP(fs->sb))
	{
		ped_exception_throw (PED_EXCEPTION_ERROR, PED_EXCEPTION_CANCEL,
			_("File system has too many allocated inodes to "
			  "remove a group!"));
		return 0;
	}

	if (fs->opt_debug)
	{
		if (EXT2_GROUP_FREE_INODES_COUNT(fs->gd[group]) !=
		    EXT2_SUPER_INODES_PER_GROUP(fs->sb))
		{
                        fputs ("ext2_del_group: this should not "
                               "happen anymore!\n", stderr);

			return 0;
		}
	}

	newgdblocks = ped_div_round_up((fs->numgroups - 1) *
			      sizeof(struct ext2_group_desc), fs->blocksize);

	if (newgdblocks != fs->gdblocks)
	{
		int i;

		for (i=0;i<fs->numgroups;i++)
			if (ext2_is_group_sparse(fs, i))
			{
				blk_t start;

				start = EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb) +
					i * EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);
				ext2_set_block_state(fs,
						     start + fs->gdblocks,
						     0, 1);
			}

		fs->gdblocks--;
		fs->adminblocks--;
		if (sparse)
			admin--;
	}

	if (fs->opt_debug)
	{
		if (EXT2_GROUP_FREE_BLOCKS_COUNT(fs->gd[group])
				!= groupsize - admin)
		{
			blk_t i;
			blk_t num;
			blk_t offset;

			offset = EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb) +
				group * EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);
			num = EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);

			for (i=0;i<num;i++)
				if (ext2_is_data_block(fs, offset+i) &&
				    ext2_get_block_state(fs, offset+i))
				{
					fprintf(stderr,
						"error: block relocator "
						"should have relocated "
						"%i\n",
						offset+i);

					return 0;
				}
		}
	}

	fs->numgroups--;

	fs->sb.s_inodes_count = PED_CPU_TO_LE32(
		EXT2_SUPER_INODES_COUNT(fs->sb)
		- EXT2_SUPER_INODES_PER_GROUP(fs->sb));
	fs->sb.s_blocks_count = PED_CPU_TO_LE32(
		EXT2_SUPER_BLOCKS_COUNT(fs->sb) - groupsize);
	fs->sb.s_free_blocks_count = PED_CPU_TO_LE32(
		EXT2_SUPER_FREE_BLOCKS_COUNT(fs->sb) - (groupsize - admin));
	fs->sb.s_free_inodes_count = PED_CPU_TO_LE32(
		EXT2_SUPER_FREE_INODES_COUNT(fs->sb)
	        - EXT2_SUPER_INODES_PER_GROUP(fs->sb));
	fs->metadirty |= EXT2_META_SB;

	if (fs->opt_safe)
		ext2_sync(fs);

	ped_realloc ((void*) &fs->gd,
		     fs->numgroups * sizeof(struct ext2_group_desc)
			      + fs->blocksize);

	return 1;
}

static int ext2_grow_group(struct ext2_fs *fs, blk_t newsize)
{
	int   group;
	blk_t groupoff;
	blk_t gblocks;
	blk_t i;

	if (fs->opt_verbose)
                fputs ("ext2_grow_group\n", stderr);

	group = fs->numgroups - 1;
	groupoff = group * EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb)
		   + EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb);
	gblocks = EXT2_SUPER_BLOCKS_COUNT(fs->sb) - groupoff;

	if (fs->opt_debug)
	{
		if (newsize < gblocks)
		{
                        fputs ("ext2_grow_group: called to shrink group!\n",
                               stderr);

			return 0;
		}

		if (gblocks == newsize)
		{
                        fputs ("ext2_grow_group: nothing to do!\n", stderr);
			return 0;
		}
	}

	for (i=gblocks;i<newsize;i++)
		ext2_set_block_state(fs, groupoff + i, 0, 1);

	fs->sb.s_blocks_count = PED_CPU_TO_LE32(
		EXT2_SUPER_BLOCKS_COUNT(fs->sb) + newsize - gblocks);
	fs->metadirty |= EXT2_META_SB;

	if (fs->opt_safe)
		ext2_sync(fs);

	return 1;
}

static int ext2_shrink_group(struct ext2_fs *fs, blk_t newsize)
{
	blk_t admin;
	int   group;
	blk_t groupoff;
	blk_t gblocks;
	blk_t i;

	if (fs->opt_verbose)
                fputs ("ext2_shrink_group\n", stderr);

	group = fs->numgroups - 1;

	admin = fs->adminblocks;
	if (!ext2_is_group_sparse(fs, group))
		admin -= fs->gdblocks + 1;

	groupoff = group * EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb)
		   + EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb);
	gblocks = EXT2_SUPER_BLOCKS_COUNT(fs->sb) - groupoff;

	if (fs->opt_debug)
	{
		if (newsize < admin)
		{
			fprintf(stderr,
				"ext2_shrink_group: cant shrink a group "
				"to %i blocks\n", newsize);

			return 0;
		}

		if (newsize > gblocks)
		{
                        fputs ("ext2_shrink_group: called to grow group!\n",
                               stderr);

			return 0;
		}

		if (gblocks == newsize)
		{
                        fputs ("ext2_shrink_group: nothing to do!\n",
                               stderr);

			return 0;
		}
	}

	for (i=newsize;i<gblocks;i++)
	{
		if (fs->opt_debug && ext2_get_block_state(fs, groupoff + i))
		{
			fprintf(stderr,
				"error: block relocator should have relocated "
				"%i\n",
				groupoff + i);

			return 0;
		}

		ext2_set_block_state(fs, groupoff + i, 1, 0);
	}

	i = gblocks - newsize;
	fs->sb.s_blocks_count = PED_CPU_TO_LE32(
		EXT2_SUPER_BLOCKS_COUNT(fs->sb) - i);
	fs->sb.s_free_blocks_count = PED_CPU_TO_LE32(
		EXT2_SUPER_FREE_BLOCKS_COUNT(fs->sb) - i);
	fs->gd[group].bg_free_blocks_count = PED_CPU_TO_LE16(
		EXT2_GROUP_FREE_BLOCKS_COUNT(fs->gd[group]) - i);

	fs->metadirty |= EXT2_META_SB | EXT2_META_GD;

	if (fs->opt_safe)
		ext2_sync(fs);

	return 1;
}






static int ext2_grow_fs(struct ext2_fs *fs, blk_t newsize, PedTimer* timer)
{
	blk_t diff;
	blk_t sizelast;
	blk_t origsize = EXT2_SUPER_BLOCKS_COUNT(fs->sb);

	if (fs->opt_verbose)
                fputs ("ext2_grow_fs\n", stderr);

	if (!ext2_block_relocate(fs, newsize))
		return 0;

	if (!ext2_metadata_push(fs, newsize))
		return 0;

	diff = newsize - EXT2_SUPER_BLOCKS_COUNT(fs->sb);
	sizelast = EXT2_SUPER_BLOCKS_COUNT(fs->sb)
		   - EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb)
		   - (fs->numgroups-1) * EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);

	if (sizelast != EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb))
	{
		blk_t growto;

		growto = sizelast + diff;
		if (growto > EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb))
			growto = EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);

		if (!ext2_grow_group(fs, growto))
			return 0;

		diff -= growto - sizelast;
	}

	ped_timer_reset (timer);
	ped_timer_set_state_name (timer, _("adding groups"));

	while (diff)
	{
		ped_timer_update (timer,
			          1.0 - 1.0 * diff / (newsize - origsize));

		sizelast = PED_MIN(diff, EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb));
		if (!ext2_add_group(fs, sizelast))
			return 0;

		diff -= sizelast;
	}

	ped_timer_update (timer, 1.0);

	return 1;
}

static int ext2_shrink_fs(struct ext2_fs *fs, blk_t newsize,
			  PedTimer* timer)
{
	blk_t origsize = EXT2_SUPER_BLOCKS_COUNT (fs->sb);
	blk_t diff;
	int newgroups;
	blk_t sizelast;

	if (fs->opt_verbose)
                fputs ("ext2_shrink_fs\n", stderr);

	newgroups = ped_div_round_up (newsize
                                - EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb),
		        EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb));
	if (EXT2_SUPER_BLOCKS_COUNT(fs->sb)
	    - EXT2_SUPER_FREE_BLOCKS_COUNT(fs->sb) > newsize)
	{
		ped_exception_throw (PED_EXCEPTION_ERROR, PED_EXCEPTION_CANCEL,
			_("Your file system is too full to resize it to %i "
			  "blocks.  Sorry."), newsize);
		return 0;
	}

	if (EXT2_SUPER_INODES_COUNT(fs->sb)
	    - EXT2_SUPER_FREE_INODES_COUNT(fs->sb)
	    		> newgroups * EXT2_SUPER_INODES_PER_GROUP(fs->sb))
	{
		ped_exception_throw (PED_EXCEPTION_ERROR, PED_EXCEPTION_CANCEL,
			_("Your file system has too many occupied inodes to "
			  "resize it to %i blocks.  Sorry."), newsize);
		return 0;
	}

	if (!ext2_inode_relocate(fs, newgroups))
		return 0;

	if (!ext2_block_relocate(fs, newsize))
		return 0;

	diff = EXT2_SUPER_BLOCKS_COUNT(fs->sb) - newsize;

	ped_timer_reset (timer);
	ped_timer_set_state_name (timer, _("shrinking"));

	while (diff > 0)
	{
		ped_timer_update (timer,
				  1.0 - 1.0 * diff / (origsize - newsize));

		sizelast = EXT2_SUPER_BLOCKS_COUNT(fs->sb)
			   - EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb) -
			   (fs->numgroups - 1)
			   	* EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);

		if (diff < sizelast)
		{
			if (!ext2_shrink_group(fs, sizelast - diff))
				return 0;

			diff = 0;
		}
		else
		{
			if (!ext2_del_group(fs))
				return 0;

			diff -= sizelast;
		}
	}
	
	ped_timer_update (timer, 1.0);

	return 1;
}

int ext2_determine_itoffset(struct ext2_fs *fs)
{
	int i;

	fs->itoffset = EXT2_GROUP_INODE_TABLE(fs->gd[0])
		       - EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb);

        /*PED_DEBUG (0x20, "itoffset is %d", fs->itoffset);
        
        PED_DEBUG (0x20, "walking %d groups", fs->numgroups);*/

	for (i=0;i<fs->numgroups;i++)
	{
		blk_t start;
		blk_t bb;
		blk_t ib;
		blk_t it;

		start = EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb)
			+ (i * EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb));
		it = start + fs->itoffset;

                /*PED_DEBUG (0x21, "start = %d, it = %d", start, it);*/

		if (ext2_is_group_sparse(fs, i))
		{
                        /*PED_DEBUG (0x21, "%d has a superblock copy", i);*/
			bb = it - 2;
			ib = it - 1;
		}
		else
		{
                        /*PED_DEBUG (0x21, "%d doesn't have a superblock copy",
                            i);*/
			bb = start;
			ib = start + 1;
		}

		if (EXT2_GROUP_BLOCK_BITMAP(fs->gd[i]) != bb ||
		    EXT2_GROUP_INODE_BITMAP(fs->gd[i]) != ib ||
		    EXT2_GROUP_INODE_TABLE(fs->gd[i]) != it)
		{
		/*	ped_exception_throw (PED_EXCEPTION_NO_FEATURE,
				PED_EXCEPTION_CANCEL,
			_("This ext2 file system has a rather strange layout!  "
			  "Parted can't resize this (yet)."));*/

                 /*       PED_DEBUG (0x21, "calculated block bitmap to be %d, "
                                         "but fs says %d.", bb,
                                         EXT2_GROUP_BLOCK_BITMAP(fs->gd[i]));
                        PED_DEBUG (0x21, "calculated inode bitmap to be %d, "
                                         "but fs says %d.", ib,
                                         EXT2_GROUP_INODE_BITMAP(fs->gd[i]));
                        PED_DEBUG (0x21, "calculated inode table to be %d, "
                                         "but fs says %d.", it,
                                         EXT2_GROUP_INODE_TABLE(fs->gd[i]));*/
                        
			return 0;
		}
	}

	return 1;
}

int ext2_resize_fs(struct ext2_fs *fs, blk_t newsize, PedTimer* timer)
{
	blk_t residue;
	int status;

	if (EXT2_SUPER_STATE(fs->sb) & EXT2_ERROR_FS)
	{
		ped_exception_throw (
			PED_EXCEPTION_WARNING, PED_EXCEPTION_CANCEL,
			_("File system has errors!  You should run e2fsck."));
		return 0;
	}

	if (!(EXT2_SUPER_STATE(fs->sb) & EXT2_VALID_FS))
	{
		ped_exception_throw (
			PED_EXCEPTION_ERROR, PED_EXCEPTION_CANCEL,
			_("File system was not cleanly unmounted!  "
			  "You should run e2fsck."));
		return 0;
	}

	if (EXT2_SUPER_FEATURE_COMPAT(fs->sb)
			& EXT2_FEATURE_COMPAT_HAS_DIR_INDEX) {
		if (ped_exception_throw (
			PED_EXCEPTION_WARNING, PED_EXCEPTION_IGNORE_CANCEL,
			_("The file system has the 'dir_index' feature "
			  "enabled.  Parted can only resize the file system "
			  "if it disables this feature.  You can enable it "
			  "later by running 'tune2fs -O dir_index DEVICE' "
			  "and then 'e2fsck -fD DEVICE'."))
				!= PED_EXCEPTION_IGNORE)
			return 0;
		fs->sb.s_feature_compat
			= PED_CPU_TO_LE32(EXT2_SUPER_FEATURE_COMPAT(fs->sb)
					  & ~EXT2_FEATURE_COMPAT_HAS_DIR_INDEX);
		fs->metadirty |= EXT2_META_SB;
	}

	if (!ext2_determine_itoffset(fs) && ped_exception_throw (
                        PED_EXCEPTION_WARNING,
                        PED_EXCEPTION_OK_CANCEL,
                        _("A resize operation on this file system will "
                          "use EXPERIMENTAL code\n"
                          "that MAY CORRUPT it (although no one has "
                          "reported any such damage yet).\n"
                          "You should at least backup your data first, "
                          "and run 'e2fsck -f' afterwards."))
                == PED_EXCEPTION_CANCEL)
        {
	        return 0;
        }

	if (fs->opt_verbose)
                fputs ("ext2_resize_fs\n", stderr);

	residue = (newsize - EXT2_SUPER_FIRST_DATA_BLOCK(fs->sb))
		   % EXT2_SUPER_BLOCKS_PER_GROUP(fs->sb);
	if (residue && residue <= fs->adminblocks)
		newsize -= residue;

	if (newsize == EXT2_SUPER_BLOCKS_COUNT(fs->sb))
		return 1;

	fs->relocator_pool
		= (unsigned char *)ped_malloc(ext2_relocator_pool_size << 10);
	if (!fs->relocator_pool)
		return 0;
	fs->relocator_pool_end
		= fs->relocator_pool + (ext2_relocator_pool_size << 10);

	if (newsize < EXT2_SUPER_BLOCKS_COUNT(fs->sb))
		status = ext2_shrink_fs(fs, newsize, timer);
	else
		status = ext2_grow_fs(fs, newsize, timer);

	ped_free(fs->relocator_pool);
	fs->relocator_pool = NULL;
	fs->relocator_pool_end = NULL;

	return status;
}
#endif /* !DISCOVER_ONLY */
