add compile-time check for correct DHCP packet size
[oweals/busybox.git] / e2fsprogs / mke2fs.c
index ab50717e7dad91d4805d2da2390eb68be07c3ced..1c4f1541e315cc5e86b6657e681d3b5e52e6f274 100644 (file)
@@ -1,3 +1,4 @@
+/* vi: set sw=4 ts=4: */
 /*
  * mke2fs.c - Make a ext2fs filesystem.
  *
@@ -107,9 +108,9 @@ static const struct mke2fs_defaults settings[] = {
        { default_str,   3, 1024, 8192 },
        { "journal",     0, 4096, 8192 },
        { "news",        0, 4096, 4096 },
-       { "largefile",   0, 4096, 1024 * 1024 },
+       { "largefile",   0, 4096, 1024 * 1024 },
        { "largefile4",  0, 4096, 4096 * 1024 },
-       { 0,             0,    0, 0},
+       { 0,             0,    0, 0},
 };
 
 static void set_fs_defaults(const char *fs_type,
@@ -176,9 +177,9 @@ static void mke2fs_error_msg_and_die(int retval, const char *fmt, ...)
 
        if (retval) {
                va_start(ap, fmt);
-               bb_fprintf(stderr,"\nCould not ");
-               bb_vfprintf(stderr, fmt, ap);
-               bb_fprintf(stderr, "\n");
+               fprintf(stderr,"\nCould not ");
+               vfprintf(stderr, fmt, ap);
+               fprintf(stderr, "\n");
                va_end(ap);
                exit(EXIT_FAILURE);
        }
@@ -191,7 +192,7 @@ static void mke2fs_verbose(const char *fmt, ...)
 
        if (!quiet) {
                va_start(ap, fmt);
-               bb_vfprintf(stdout, fmt, ap);
+               vfprintf(stdout, fmt, ap);
                fflush(stdout);
                va_end(ap);
        }
@@ -209,9 +210,9 @@ static void mke2fs_warning_msg(int retval, char *fmt, ... )
 
        if (retval) {
                va_start(ap, fmt);
-               bb_fprintf(stderr,"\nWarning: ");
-               bb_vfprintf(stderr, fmt, ap);
-               bb_fprintf(stderr, "\n");
+               fprintf(stderr,"\nWarning: ");
+               vfprintf(stderr, fmt, ap);
+               fprintf(stderr, "\n");
                va_end(ap);
        }
 }
@@ -225,7 +226,7 @@ static void read_bb_file(ext2_filsys fs, badblocks_list *bb_list,
        FILE            *f;
        errcode_t       retval;
 
-       f = bb_xfopen(bad_blocks_file, "r");
+       f = xfopen(bad_blocks_file, "r");
        retval = ext2fs_read_bb_FILE(fs, f, bb_list, invalid_block);
        fclose (f);
        mke2fs_error_msg_and_die(retval, "read bad blocks from list");
@@ -246,7 +247,7 @@ static void test_disk(ext2_filsys fs, badblocks_list *bb_list)
        mke2fs_verbose("Running command: %s\n", buf);
        f = popen(buf, "r");
        if (!f) {
-               bb_perror_msg_and_die("Could not run '%s'", buf);
+               bb_perror_msg_and_die("cannot run '%s'", buf);
        }
        retval = ext2fs_read_bb_FILE(fs, f, bb_list, invalid_block);
        pclose(f);
@@ -400,7 +401,7 @@ static errcode_t zero_blocks(ext2_filsys fs, blk_t blk, int num,
        }
        /* Allocate the zeroizing buffer if necessary */
        if (!buf) {
-               buf = xcalloc(fs->blocksize, STRIDE_LENGTH);
+               buf = xzalloc(fs->blocksize * STRIDE_LENGTH);
        }
        /* OK, do the write loop */
        next_update = 0;
@@ -448,7 +449,7 @@ static void write_inode_tables(ext2_filsys fs)
                num = fs->inode_blocks_per_group;
 
                retval = zero_blocks(fs, blk, num, 0, &blk, &num);
-               mke2fs_error_msg_and_die(retval, 
+               mke2fs_error_msg_and_die(retval,
                        "write %d blocks in inode table starting at %d.",
                        num, blk);
                if (sync_kludge) {
@@ -572,7 +573,7 @@ static void zap_sector(ext2_filsys fs, int sect, int nsect)
 
 static void create_journal_dev(ext2_filsys fs)
 {
-       struct progress_struct  progress;
+       struct progress_struct  progress;
        errcode_t               retval;
        char                    *buf;
        char                    *fmt = "%s journal superblock";
@@ -624,7 +625,7 @@ static void show_stats(ext2_filsys fs)
                        os,
                        fs->blocksize, s->s_log_block_size,
                        fs->fragsize, s->s_log_frag_size,
-                       s->s_inodes_count, s->s_blocks_count, 
+                       s->s_inodes_count, s->s_blocks_count,
                        s->s_r_blocks_count, 100.0 * s->s_r_blocks_count / s->s_blocks_count,
                        s->s_first_data_block);
        free(os);
@@ -679,21 +680,19 @@ static int set_os(struct ext2_super_block *sb, char *os)
        if((sb->s_creator_os = e2p_string2os(os)) >= 0) {
                return 1;
        } else if (!strcasecmp("GNU", os)) {
-               sb->s_creator_os = EXT2_OS_HURD;
+               sb->s_creator_os = EXT2_OS_HURD;
                return 1;
        }
        return 0;
 }
 
-#define PATH_SET "PATH=/sbin"
-
 static void parse_extended_opts(struct ext2_super_block *sb_param,
                                const char *opts)
 {
        char    *buf, *token, *next, *p, *arg;
        int     r_usage = 0;
 
-       buf = bb_xstrdup(opts);
+       buf = xstrdup(opts);
        for (token = buf; token && *token; token = next) {
                p = strchr(token, ',');
                next = 0;
@@ -713,7 +712,7 @@ static void parse_extended_opts(struct ext2_super_block *sb_param,
                        }
                        fs_stride = strtoul(arg, &p, 0);
                        if (*p || (fs_stride == 0)) {
-                               bb_error_msg("Invalid stride parameter");
+                               bb_error_msg("Invalid stride parameter: %s", arg);
                                r_usage++;
                                continue;
                        }
@@ -737,7 +736,8 @@ static void parse_extended_opts(struct ext2_super_block *sb_param,
                                continue;
                        }
                        if (resize <= sb_param->s_blocks_count) {
-                               bb_error_msg("The resize maximum must be greater than the filesystem size");
+                               bb_error_msg("The resize maximum must be greater "
+                                               "than the filesystem size");
                                r_usage++;
                                continue;
                        }
@@ -769,10 +769,10 @@ static void parse_extended_opts(struct ext2_super_block *sb_param,
        if (r_usage) {
                bb_error_msg_and_die(
                        "\nBad options specified.\n\n"
-                       "Options are separated by commas, "
+                       "Extended options are separated by commas, "
                        "and may take an argument which\n"
                        "\tis set off by an equals ('=') sign.\n\n"
-                       "Valid raid options are:\n"
+                       "Valid extended options are:\n"
                        "\tstride=<stride length in blocks>\n"
                        "\tresize=<resize maximum size in blocks>\n");
        }
@@ -801,17 +801,13 @@ static int PRS(int argc, char *argv[])
        int             show_version_only = 0;
        ext2_ino_t      num_inodes = 0;
        errcode_t       retval;
-       char *          oldpath = getenv("PATH");
        char *          extended_opts = 0;
        const char *    fs_type = 0;
        blk_t           dev_size;
        long            sysval;
 
        /* Update our PATH to include /sbin  */
-       if (oldpath) {
-               putenv (bb_xasprintf("%s:%s", PATH_SET, oldpath));
-       } else
-               putenv (PATH_SET);
+       e2fs_set_sbin_path();
 
        tmp = getenv("MKE2FS_SYNC");
        if (tmp)
@@ -833,13 +829,10 @@ static int PRS(int argc, char *argv[])
        param.s_rev_level = 1;  /* Create revision 1 filesystems now */
        param.s_feature_incompat |= EXT2_FEATURE_INCOMPAT_FILETYPE;
        param.s_feature_ro_compat |= EXT2_FEATURE_RO_COMPAT_SPARSE_SUPER;
-#if 0
-       param.s_feature_compat |= EXT2_FEATURE_COMPAT_DIR_INDEX;
-#endif
 
 #ifdef __linux__
-       linux_version_code = get_kernel_revision();
-       if (linux_version_code && linux_version_code < (2*65536 + 2*256)) {
+       linux_version_code = get_linux_version_code();
+       if (linux_version_code && linux_version_code < KERNEL_VERSION(2,2,0)) {
                param.s_rev_level = 0;
                param.s_feature_incompat = 0;
                param.s_feature_compat = 0;
@@ -848,7 +841,7 @@ static int PRS(int argc, char *argv[])
 #endif
 
        /* If called as mkfs.ext3, create a journal inode */
-       if (last_char_is(bb_applet_name, '3')) 
+       if (last_char_is(applet_name, '3'))
                journal_size = -1;
 
        while ((c = getopt (argc, argv,
@@ -861,7 +854,7 @@ static int PRS(int argc, char *argv[])
                        if (b < EXT2_MIN_BLOCK_SIZE ||
                            b > EXT2_MAX_BLOCK_SIZE) {
 BLOCKSIZE_ERROR:
-                               bb_error_msg_and_die("bad block size - %s", optarg);
+                               bb_error_msg_and_die("invalid block size - %s", optarg);
                        }
                        mke2fs_warning_msg((blocksize > 4096),
                                "blocksize %d not usable on most systems",
@@ -877,25 +870,29 @@ BLOCKSIZE_ERROR:
                        break;
                case 'f':
                        if (safe_strtoi(optarg, &size) || size < EXT2_MIN_BLOCK_SIZE || size > EXT2_MAX_BLOCK_SIZE ){
-                               bb_error_msg_and_die("bad fragment size - %s", optarg);
+                               bb_error_msg_and_die("invalid fragment size - %s", optarg);
                        }
                        param.s_log_frag_size =
                                int_log2(size >> EXT2_MIN_BLOCK_LOG_SIZE);
                        mke2fs_warning_msg(1, "fragments not supported. Ignoring -f option");
                        break;
                case 'g':
-                       if (safe_strtoi(optarg, &param.s_blocks_per_group)) {
+                       {
+                           int foo;
+                           if (safe_strtoi(optarg, &foo)) {
                                bb_error_msg_and_die("Illegal number for blocks per group");
+                           }
+                           param.s_blocks_per_group = foo;
                        }
                        if ((param.s_blocks_per_group % 8) != 0) {
                                bb_error_msg_and_die("blocks per group must be multiple of 8");
                        }
                        break;
                case 'i':
-                       if (safe_strtoi(optarg, &inode_ratio) 
-                               || inode_ratio < EXT2_MIN_BLOCK_SIZE 
+                       if (safe_strtoi(optarg, &inode_ratio)
+                               || inode_ratio < EXT2_MIN_BLOCK_SIZE
                                || inode_ratio > EXT2_MAX_BLOCK_SIZE * 1024) {
-                               bb_error_msg_and_die("bad inode ratio %s (min %d/max %d)",
+                               bb_error_msg_and_die("invalid inode ratio %s (min %d/max %d)",
                                        optarg, EXT2_MIN_BLOCK_SIZE,
                                        EXT2_MAX_BLOCK_SIZE);
                                }
@@ -914,7 +911,7 @@ BLOCKSIZE_ERROR:
                        break;
                case 'm':
                        if (safe_strtoi(optarg, &reserved_ratio) || reserved_ratio > 50 ) {
-                               bb_error_msg_and_die("bad reserved blocks percent - %s", optarg);
+                               bb_error_msg_and_die("invalid reserved blocks percent - %s", optarg);
                        }
                        break;
                case 'n':
@@ -942,7 +939,7 @@ BLOCKSIZE_ERROR:
 #ifdef EXT2_DYNAMIC_REV
                case 'I':
                        if (safe_strtoi(optarg, &inode_size)) {
-                               bb_error_msg_and_die("bad inode size - %s", optarg);
+                               bb_error_msg_and_die("invalid inode size - %s", optarg);
                        }
                        break;
 #endif
@@ -1053,7 +1050,7 @@ BLOCKSIZE_ERROR:
        if (optind < argc) {
                param.s_blocks_count = parse_num_blocks(argv[optind++],
                                param.s_log_block_size);
-               mke2fs_error_msg_and_die(!param.s_blocks_count, "bad blocks count - %s", argv[optind - 1]);
+               mke2fs_error_msg_and_die(!param.s_blocks_count, "invalid blocks count - %s", argv[optind - 1]);
        }
        if (optind < argc)
                bb_show_usage();
@@ -1167,11 +1164,16 @@ BLOCKSIZE_ERROR:
                }
        }
 
+       if (!force && param.s_blocks_count >= (1 << 31)) {
+               bb_error_msg_and_die("Filesystem too large.  No more than 2**31-1 blocks\n"
+                       "\t (8TB using a blocksize of 4k) are currently supported.");
+       }
+
        if (inode_size) {
                if (inode_size < EXT2_GOOD_OLD_INODE_SIZE ||
                    inode_size > EXT2_BLOCK_SIZE(&param) ||
                    inode_size & (inode_size - 1)) {
-                       bb_error_msg_and_die("bad inode size %d (min %d/max %d)",
+                       bb_error_msg_and_die("invalid inode size %d (min %d/max %d)",
                                inode_size, EXT2_GOOD_OLD_INODE_SIZE,
                                blocksize);
                }
@@ -1195,7 +1197,7 @@ BLOCKSIZE_ERROR:
        return 1;
 }
 
-static void clean_up(void)
+static void mke2fs_clean_up(void)
 {
        if (ENABLE_FEATURE_CLEAN_UP && journal_device) free(journal_device);
 }
@@ -1210,7 +1212,7 @@ int mke2fs_main (int argc, char *argv[])
        io_manager      io_ptr;
 
        if (ENABLE_FEATURE_CLEAN_UP)
-               atexit(clean_up);
+               atexit(mke2fs_clean_up);
        if(!PRS(argc, argv))
                return 0;
 
@@ -1330,7 +1332,7 @@ int mke2fs_main (int argc, char *argv[])
                        retval = zero_blocks(fs, start, blocks - start,
                                             NULL, &ret_blk, NULL);
 
-               mke2fs_warning_msg(retval, "could not zero block %u at end of filesystem", ret_blk);
+               mke2fs_warning_msg(retval, "cannot zero block %u at end of filesystem", ret_blk);
                write_inode_tables(fs);
                create_root_dir(fs);
                create_lost_and_found(fs);