]> pilppa.org Git - linux-2.6-omap-h63xx.git/blobdiff - fs/ext4/super.c
Merge branch 'linus' into core/softlockup
[linux-2.6-omap-h63xx.git] / fs / ext4 / super.c
index de9d3d0eb20381054acd67af1341fa66e5764fcd..1cb371dcd609aae5f115cf236acd4d0c66956efb 100644 (file)
@@ -574,6 +574,11 @@ static struct inode *ext4_alloc_inode(struct super_block *sb)
        INIT_LIST_HEAD(&ei->i_prealloc_list);
        spin_lock_init(&ei->i_prealloc_lock);
        jbd2_journal_init_jbd_inode(&ei->jinode, &ei->vfs_inode);
+       ei->i_reserved_data_blocks = 0;
+       ei->i_reserved_meta_blocks = 0;
+       ei->i_allocated_meta_blocks = 0;
+       ei->i_delalloc_reserved_flag = 0;
+       spin_lock_init(&(ei->i_block_reservation_lock));
        return &ei->vfs_inode;
 }
 
@@ -751,6 +756,9 @@ static int ext4_show_options(struct seq_file *seq, struct vfsmount *vfs)
                seq_puts(seq, ",nomballoc");
        if (test_opt(sb, I_VERSION))
                seq_puts(seq, ",i_version");
+       if (!test_opt(sb, DELALLOC))
+               seq_puts(seq, ",nodelalloc");
+
 
        if (sbi->s_stripe)
                seq_printf(seq, ",stripe=%lu", sbi->s_stripe);
@@ -898,7 +906,7 @@ enum {
        Opt_jqfmt_vfsold, Opt_jqfmt_vfsv0, Opt_quota, Opt_noquota,
        Opt_ignore, Opt_barrier, Opt_err, Opt_resize, Opt_usrquota,
        Opt_grpquota, Opt_extents, Opt_noextents, Opt_i_version,
-       Opt_mballoc, Opt_nomballoc, Opt_stripe, Opt_delalloc,
+       Opt_mballoc, Opt_nomballoc, Opt_stripe, Opt_delalloc, Opt_nodelalloc,
 };
 
 static match_table_t tokens = {
@@ -958,6 +966,7 @@ static match_table_t tokens = {
        {Opt_stripe, "stripe=%u"},
        {Opt_resize, "resize"},
        {Opt_delalloc, "delalloc"},
+       {Opt_nodelalloc, "nodelalloc"},
        {Opt_err, NULL},
 };
 
@@ -995,6 +1004,7 @@ static int parse_options (char *options, struct super_block *sb,
        int qtype, qfmt;
        char *qname;
 #endif
+       ext4_fsblk_t last_block;
 
        if (!options)
                return 1;
@@ -1314,15 +1324,39 @@ set_qf_format:
                        clear_opt(sbi->s_mount_opt, NOBH);
                        break;
                case Opt_extents:
+                       if (!EXT4_HAS_INCOMPAT_FEATURE(sb,
+                                       EXT4_FEATURE_INCOMPAT_EXTENTS)) {
+                               ext4_warning(sb, __func__,
+                                       "extents feature not enabled "
+                                       "on this filesystem, use tune2fs\n");
+                               return 0;
+                       }
                        set_opt (sbi->s_mount_opt, EXTENTS);
                        break;
                case Opt_noextents:
+                       /*
+                        * When e2fsprogs support resizing an already existing
+                        * ext3 file system to greater than 2**32 we need to
+                        * add support to block allocator to handle growing
+                        * already existing block  mapped inode so that blocks
+                        * allocated for them fall within 2**32
+                        */
+                       last_block = ext4_blocks_count(sbi->s_es) - 1;
+                       if (last_block  > 0xffffffffULL) {
+                               printk(KERN_ERR "EXT4-fs: Filesystem too "
+                                               "large to mount with "
+                                               "-o noextents options\n");
+                               return 0;
+                       }
                        clear_opt (sbi->s_mount_opt, EXTENTS);
                        break;
                case Opt_i_version:
                        set_opt(sbi->s_mount_opt, I_VERSION);
                        sb->s_flags |= MS_I_VERSION;
                        break;
+               case Opt_nodelalloc:
+                       clear_opt(sbi->s_mount_opt, DELALLOC);
+                       break;
                case Opt_mballoc:
                        set_opt(sbi->s_mount_opt, MBALLOC);
                        break;
@@ -1970,15 +2004,28 @@ static int ext4_fill_super (struct super_block *sb, void *data, int silent)
 
        /*
         * turn on extents feature by default in ext4 filesystem
-        * User -o noextents to turn it off
+        * only if feature flag already set by mkfs or tune2fs.
+        * Use -o noextents to turn it off
         */
-       set_opt(sbi->s_mount_opt, EXTENTS);
+       if (EXT4_HAS_INCOMPAT_FEATURE(sb, EXT4_FEATURE_INCOMPAT_EXTENTS))
+               set_opt(sbi->s_mount_opt, EXTENTS);
+       else
+               ext4_warning(sb, __func__,
+                       "extents feature not enabled on this filesystem, "
+                       "use tune2fs.\n");
        /*
-        * turn on mballoc feature by default in ext4 filesystem
-        * User -o nomballoc to turn it off
+        * turn on mballoc code by default in ext4 filesystem
+        * Use -o nomballoc to turn it off
         */
        set_opt(sbi->s_mount_opt, MBALLOC);
 
+       /*
+        * enable delayed allocation by default
+        * Use -o nodelalloc to turn it off
+        */
+       set_opt(sbi->s_mount_opt, DELALLOC);
+
+
        if (!parse_options ((char *) data, sb, &journal_inum, &journal_devnum,
                            NULL, 0))
                goto failed_mount;
@@ -2417,6 +2464,13 @@ static int ext4_fill_super (struct super_block *sb, void *data, int silent)
                test_opt(sb,DATA_FLAGS) == EXT4_MOUNT_ORDERED_DATA ? "ordered":
                "writeback");
 
+       if (test_opt(sb, DATA_FLAGS) == EXT4_MOUNT_JOURNAL_DATA) {
+               printk(KERN_WARNING "EXT4-fs: Ignoring delalloc option - "
+                               "requested data journaling mode\n");
+               clear_opt(sbi->s_mount_opt, DELALLOC);
+       } else if (test_opt(sb, DELALLOC))
+               printk(KERN_INFO "EXT4-fs: delayed allocation enabled\n");
+
        ext4_ext_init(sb);
        ext4_mb_init(sb, needs_recovery);