Merge tag 'ext4_for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tytso...
[firefly-linux-kernel-4.4.55.git] / fs / ext4 / super.c
index 63e802b8ec688d626fd438d8c09b8b96b8bc8da0..43c92b1685cbff914240436f4d0901861c9fd2c2 100644 (file)
@@ -176,15 +176,6 @@ void *ext4_kvzalloc(size_t size, gfp_t flags)
        return ret;
 }
 
-void ext4_kvfree(void *ptr)
-{
-       if (is_vmalloc_addr(ptr))
-               vfree(ptr);
-       else
-               kfree(ptr);
-
-}
-
 ext4_fsblk_t ext4_block_bitmap(struct super_block *sb,
                               struct ext4_group_desc *bg)
 {
@@ -811,8 +802,8 @@ static void ext4_put_super(struct super_block *sb)
 
        for (i = 0; i < sbi->s_gdb_count; i++)
                brelse(sbi->s_group_desc[i]);
-       ext4_kvfree(sbi->s_group_desc);
-       ext4_kvfree(sbi->s_flex_groups);
+       kvfree(sbi->s_group_desc);
+       kvfree(sbi->s_flex_groups);
        percpu_counter_destroy(&sbi->s_freeclusters_counter);
        percpu_counter_destroy(&sbi->s_freeinodes_counter);
        percpu_counter_destroy(&sbi->s_dirs_counter);
@@ -880,10 +871,10 @@ static struct inode *ext4_alloc_inode(struct super_block *sb)
        spin_lock_init(&ei->i_prealloc_lock);
        ext4_es_init_tree(&ei->i_es_tree);
        rwlock_init(&ei->i_es_lock);
-       INIT_LIST_HEAD(&ei->i_es_lru);
+       INIT_LIST_HEAD(&ei->i_es_list);
        ei->i_es_all_nr = 0;
-       ei->i_es_lru_nr = 0;
-       ei->i_touch_when = 0;
+       ei->i_es_shk_nr = 0;
+       ei->i_es_shrink_lblk = 0;
        ei->i_reserved_data_blocks = 0;
        ei->i_reserved_meta_blocks = 0;
        ei->i_allocated_meta_blocks = 0;
@@ -973,7 +964,6 @@ void ext4_clear_inode(struct inode *inode)
        dquot_drop(inode);
        ext4_discard_preallocations(inode);
        ext4_es_remove_extent(inode, 0, EXT_MAX_BLOCKS);
-       ext4_es_lru_del(inode);
        if (EXT4_I(inode)->jinode) {
                jbd2_journal_release_jbd_inode(EXT4_JOURNAL(inode),
                                               EXT4_I(inode)->jinode);
@@ -1153,7 +1143,7 @@ enum {
        Opt_inode_readahead_blks, Opt_journal_ioprio,
        Opt_dioread_nolock, Opt_dioread_lock,
        Opt_discard, Opt_nodiscard, Opt_init_itable, Opt_noinit_itable,
-       Opt_max_dir_size_kb,
+       Opt_max_dir_size_kb, Opt_nojournal_checksum,
 };
 
 static const match_table_t tokens = {
@@ -1187,6 +1177,7 @@ static const match_table_t tokens = {
        {Opt_journal_dev, "journal_dev=%u"},
        {Opt_journal_path, "journal_path=%s"},
        {Opt_journal_checksum, "journal_checksum"},
+       {Opt_nojournal_checksum, "nojournal_checksum"},
        {Opt_journal_async_commit, "journal_async_commit"},
        {Opt_abort, "abort"},
        {Opt_data_journal, "data=journal"},
@@ -1368,6 +1359,8 @@ static const struct mount_opts {
         MOPT_EXT4_ONLY | MOPT_SET | MOPT_EXPLICIT},
        {Opt_nodelalloc, EXT4_MOUNT_DELALLOC,
         MOPT_EXT4_ONLY | MOPT_CLEAR},
+       {Opt_nojournal_checksum, EXT4_MOUNT_JOURNAL_CHECKSUM,
+        MOPT_EXT4_ONLY | MOPT_CLEAR},
        {Opt_journal_checksum, EXT4_MOUNT_JOURNAL_CHECKSUM,
         MOPT_EXT4_ONLY | MOPT_SET},
        {Opt_journal_async_commit, (EXT4_MOUNT_JOURNAL_ASYNC_COMMIT |
@@ -1709,6 +1702,12 @@ static int parse_options(char *options, struct super_block *sb,
                        return 0;
                }
        }
+       if (test_opt(sb, DATA_FLAGS) == EXT4_MOUNT_ORDERED_DATA &&
+           test_opt(sb, JOURNAL_ASYNC_COMMIT)) {
+               ext4_msg(sb, KERN_ERR, "can't mount with journal_async_commit "
+                        "in data=ordered mode");
+               return 0;
+       }
        return 1;
 }
 
@@ -1946,7 +1945,7 @@ int ext4_alloc_flex_bg_array(struct super_block *sb, ext4_group_t ngroup)
                memcpy(new_groups, sbi->s_flex_groups,
                       (sbi->s_flex_groups_allocated *
                        sizeof(struct flex_groups)));
-               ext4_kvfree(sbi->s_flex_groups);
+               kvfree(sbi->s_flex_groups);
        }
        sbi->s_flex_groups = new_groups;
        sbi->s_flex_groups_allocated = size / sizeof(struct flex_groups);
@@ -3317,7 +3316,7 @@ int ext4_calculate_overhead(struct super_block *sb)
        struct ext4_super_block *es = sbi->s_es;
        ext4_group_t i, ngroups = ext4_get_groups_count(sb);
        ext4_fsblk_t overhead = 0;
-       char *buf = (char *) get_zeroed_page(GFP_KERNEL);
+       char *buf = (char *) get_zeroed_page(GFP_NOFS);
 
        if (!buf)
                return -ENOMEM;
@@ -3345,8 +3344,8 @@ int ext4_calculate_overhead(struct super_block *sb)
                        memset(buf, 0, PAGE_SIZE);
                cond_resched();
        }
-       /* Add the journal blocks as well */
-       if (sbi->s_journal)
+       /* Add the internal journal blocks as well */
+       if (sbi->s_journal && !sbi->journal_bdev)
                overhead += EXT4_NUM_B2C(sbi, sbi->s_journal->j_maxlen);
 
        sbi->s_overhead = overhead;
@@ -4232,7 +4231,7 @@ failed_mount7:
 failed_mount6:
        ext4_mb_release(sb);
        if (sbi->s_flex_groups)
-               ext4_kvfree(sbi->s_flex_groups);
+               kvfree(sbi->s_flex_groups);
        percpu_counter_destroy(&sbi->s_freeclusters_counter);
        percpu_counter_destroy(&sbi->s_freeinodes_counter);
        percpu_counter_destroy(&sbi->s_dirs_counter);
@@ -4261,7 +4260,7 @@ failed_mount3:
 failed_mount2:
        for (i = 0; i < db_count; i++)
                brelse(sbi->s_group_desc[i]);
-       ext4_kvfree(sbi->s_group_desc);
+       kvfree(sbi->s_group_desc);
 failed_mount:
        if (sbi->s_chksum_driver)
                crypto_free_shash(sbi->s_chksum_driver);
@@ -4862,6 +4861,14 @@ static int ext4_remount(struct super_block *sb, int *flags, char *data)
                goto restore_opts;
        }
 
+       if ((old_opts.s_mount_opt & EXT4_MOUNT_JOURNAL_CHECKSUM) ^
+           test_opt(sb, JOURNAL_CHECKSUM)) {
+               ext4_msg(sb, KERN_ERR, "changing journal_checksum "
+                        "during remount not supported");
+               err = -EINVAL;
+               goto restore_opts;
+       }
+
        if (test_opt(sb, DATA_FLAGS) == EXT4_MOUNT_JOURNAL_DATA) {
                if (test_opt2(sb, EXPLICIT_DELALLOC)) {
                        ext4_msg(sb, KERN_ERR, "can't mount with "