From f4b2a6db3f13f4210697bcd273086006c719929b Mon Sep 17 00:00:00 2001 From: Theodore Ts'o Date: Sat, 21 Feb 1998 04:20:44 +0000 Subject: [PATCH] ChangeLog, main.c, resize2fs.8.in, resize2fs.c: main.c (check_mount, main): Resize2fs now checks the size of the partition, and uses this as a default new_size of the partition if one is not specified. Resize2fs will not let you resize a mounted partition. resize2fs.c: Change how the progress function for the INODE_SCAN pass is performed, so that the maximum size is never zero. resize2fs.8.in: Updated man page. --- resize/ChangeLog | 12 +++++++ resize/main.c | 91 ++++++++++++++++++++++++++++++++++++++++++++++----- resize/resize2fs.8.in | 49 ++++++++++++++++++++++----- resize/resize2fs.c | 10 +++--- 4 files changed, 140 insertions(+), 22 deletions(-) diff --git a/resize/ChangeLog b/resize/ChangeLog index 8c54be7..a4eabff 100644 --- a/resize/ChangeLog +++ b/resize/ChangeLog @@ -1,3 +1,15 @@ +1998-02-20 Theodore Y. Ts'o + + * main.c (check_mount, main): Resize2fs now checks the size of the + partition, and uses this as a default new_size of the + partition if one is not specified. Resize2fs will not let + you resize a mounted partition. + + * resize2fs.c: Change how the progress function for the INODE_SCAN + pass is performed, so that the maximum size is never zero. + + * resize2fs.8.in: Updated man page. + Mon Feb 16 17:13:01 1998 Theodore Ts'o * resize2fs.c, resize2fs.h, main.c, ext2_block_move.c, diff --git a/resize/main.c b/resize/main.c index c547f07..7e25a8a 100644 --- a/resize/main.c +++ b/resize/main.c @@ -24,7 +24,7 @@ char *program_name, *device_name; static volatile void usage (char *prog) { - fprintf (stderr, "usage: %s [-d debug_flags] [-p] [-F] device new-size\n", prog); + fprintf (stderr, "usage: %s [-d debug_flags] [-f] [-F] [-p] device new-size\n", prog); exit (1); } @@ -36,6 +36,8 @@ static void resize_progress_func(ext2_resize_t rfs, int pass, errcode_t retval; progress = (ext2_sim_progmeter) rfs->prog_data; + if (max == 0) + return; if (cur == 0) { if (progress) ext2fs_progress_close(progress); @@ -77,6 +79,27 @@ static void resize_progress_func(ext2_resize_t rfs, int pass, } } +static void check_mount(char *device_name) +{ + errcode_t retval; + int mount_flags; + + retval = ext2fs_check_if_mounted(device_name, &mount_flags); + if (retval) { + com_err("ext2fs_check_if_mount", retval, + "while determining whether %s is mounted.", + device_name); + return; + } + if (!(mount_flags & EXT2_MF_MOUNTED)) + return; + + fprintf(stderr, "%s is mounted; can't resize a " + "mounted filesystem!\n\n", device_name); + exit(1); +} + + void main (int argc, char ** argv) { errcode_t retval; @@ -84,9 +107,14 @@ void main (int argc, char ** argv) int c; int flags = 0; int flush = 0; + int force = 0; int fd; - blk_t new_size; + blk_t new_size = 0; + blk_t max_size = 0; io_manager io_ptr; + char *tmp; + + initialize_ext2_error_table(); fprintf (stderr, "resize2fs %s, %s for EXT2 FS %s, %s\n", E2FSPROGS_VERSION, E2FSPROGS_DATE, @@ -94,11 +122,14 @@ void main (int argc, char ** argv) if (argc && *argv) program_name = *argv; - while ((c = getopt (argc, argv, "d:Fhp")) != EOF) { + while ((c = getopt (argc, argv, "d:fFhp")) != EOF) { switch (c) { case 'h': usage(program_name); break; + case 'f': + force = 1; + break; case 'F': flush = 1; break; @@ -109,15 +140,25 @@ void main (int argc, char ** argv) flags |= RESIZE_PERCENT_COMPLETE; break; default: - usage (program_name); + usage(program_name); } } - if (optind > argc - 2) - usage (program_name); + if (optind == argc) + usage(program_name); device_name = argv[optind++]; - new_size = atoi(argv[optind++]); - initialize_ext2_error_table(); - + if (optind < argc) { + new_size = strtoul(argv[optind++], &tmp, 0); + if (*tmp) { + com_err(program_name, 0, "bad filesystem size - %s", + argv[optind - 1]); + exit(1); + } + } + if (optind < argc) + usage(program_name); + + check_mount(device_name); + if (flush) { #ifdef BLKFLSBUF fd = open(device_name, O_RDONLY, 0); @@ -153,6 +194,38 @@ void main (int argc, char ** argv) printf ("Couldn't find valid filesystem superblock.\n"); exit (1); } + + /* + * Get the size of the containing partition, and use this for + * defaults and for making sure the new filesystme doesn't + * exceed the partition size. + */ + retval = ext2fs_get_device_size(device_name, fs->blocksize, + &max_size); + if (retval) { + com_err(program_name, retval, + "while trying to determine filesystem size"); + exit(1); + } + if (!new_size) + new_size = max_size; + if (!force && (new_size > max_size)) { + fprintf(stderr, "The containing partition (or device)" + " is only %d blocks.\nYou requested a new size" + " of %d blocks.\n\n", max_size, + new_size); + exit(1); + } + if (new_size == fs->super->s_blocks_count) { + fprintf(stderr, "The filesystem is already %d blocks " + "long. Nothing to do!\n\n", new_size); + exit(0); + } + if (!force && (fs->super->s_lastcheck < fs->super->s_mtime)) { + fprintf(stderr, "Please run 'e2fsck -f %s' first.\n\n", + device_name); + exit(1); + } retval = resize_fs(fs, new_size, flags, ((flags & RESIZE_PERCENT_COMPLETE) ? resize_progress_func : 0)); diff --git a/resize/resize2fs.8.in b/resize/resize2fs.8.in index ac2c7fd..3e60ce5 100644 --- a/resize/resize2fs.8.in +++ b/resize/resize2fs.8.in @@ -11,27 +11,57 @@ resize2fs \- ext2 file system resizer .I debug-flags ] [ -.B \-p +.B \-f ] [ .B \-F ] +[ +.B \-p +] .I device +[ .I size +] .SH DESCRIPTION The .B resize2fs program will resize ext2 file systems. It can be used to enlarge or -shrink an ext2 file system so that it will have +shrink an ext2 file system located on +.I device +so that it will have .I size blocks. -The device containing the ext2 filesystem is specified by the -.I device -parameter. +If the +.I size +parameter is not specified, it will default to the size of the partition. +The +.I size +parameter may never be larger than the size of the partition. +.PP +The +.B resize2fs +program does not manipulate the size of partitions. If you wish to enlarge +a filesystem, you must first make sure you can expand the size of the +underlying partition first. This can be done using +.BR fdisk (8) +by deleting the partition and recreating it with a larger size. When +recreating the partition, make sure you create it with the same starting +disk cylinder as before! Otherwise, the resize operation will +certainly not work, and you may lose your entire filesystem. +.PP +If you wish to shrink the an ext2 partition, first use +.B resize2fs +to shrink the size of filesystem. Then you may use +.BR fdisk (8) +to shrink the size of the partition. When shrinking the size of +the partition, make sure you do not make it smaller than the new size +of the ext2 filesystem! .SH OPTIONS .TP .I \-d debug-flags -Turns on various resize2fs debugging features. +Turns on various resize2fs debugging features, if they have been compiled +into the binary. .I debug-flags should be computed by adding the numbers of the desired features from the following list: @@ -50,6 +80,10 @@ Prints out a percentage completion bars for each operation, so that the user can keep track of what the program is doing. .TP +.I \-f +Forces resize2fs to proceed with the filesystem resize operation, overriding +some safety checks which resize2fs normally enforces. +.TP .I \-F Flush the filesystem device's buffer caches before beginning. Only really useful for doing @@ -59,7 +93,6 @@ time trials. .B resize2fs was written by Theodore Ts'o . .SH SEE ALSO -.BR dumpe2fs (8), -.BR tune2fs (8), +.BR fdisk (8), .BR e2fsck (8), .BR mke2fs (8) diff --git a/resize/resize2fs.c b/resize/resize2fs.c index cffc355..30b6c8d 100644 --- a/resize/resize2fs.c +++ b/resize/resize2fs.c @@ -882,16 +882,16 @@ static errcode_t progress_callback(ext2_filsys fs, ext2_inode_scan scan, ext2_resize_t rfs = (ext2_resize_t) priv_data; /* - * The if (group+1) == 0 test is to protect against old ext2 - * libraries. It shouldn't be needed against new libraries. + * This check is to protect against old ext2 libraries. It + * shouldn't be needed against new libraries. */ - if (group == 0 || (group+1) == 0) + if ((group+1) == 0) return 0; if (rfs->progress) { io_channel_flush(fs->io); (rfs->progress)(rfs, E2_RSZ_INODE_SCAN_PASS, - group, fs->group_desc_count-1); + group+1, fs->group_desc_count); } return 0; @@ -927,7 +927,7 @@ static errcode_t inode_scan_and_fix(ext2_resize_t rfs) if (rfs->progress) (rfs->progress)(rfs, E2_RSZ_INODE_SCAN_PASS, - 0, rfs->old_fs->group_desc_count-1); + 0, rfs->old_fs->group_desc_count); ext2fs_set_inode_callback(scan, progress_callback, (void *) rfs); pb.rfs = rfs; -- 1.8.3.1