ext4: Replace open coded mdata csum feature to helper function
[firefly-linux-kernel-4.4.55.git] / fs / ext4 / super.c
index fb219b95f8d2ab7d527ef115e80578ec6792f10c..5afe42db303cad023fe58a20e142994949176f9e 100644 (file)
@@ -70,7 +70,6 @@ static void ext4_mark_recovery_complete(struct super_block *sb,
 static void ext4_clear_journal_err(struct super_block *sb,
                                   struct ext4_super_block *es);
 static int ext4_sync_fs(struct super_block *sb, int wait);
-static int ext4_sync_fs_nojournal(struct super_block *sb, int wait);
 static int ext4_remount(struct super_block *sb, int *flags, char *data);
 static int ext4_statfs(struct dentry *dentry, struct kstatfs *buf);
 static int ext4_unfreeze(struct super_block *sb);
@@ -141,8 +140,7 @@ static __le32 ext4_superblock_csum(struct super_block *sb,
 static int ext4_superblock_csum_verify(struct super_block *sb,
                                       struct ext4_super_block *es)
 {
-       if (!EXT4_HAS_RO_COMPAT_FEATURE(sb,
-                                      EXT4_FEATURE_RO_COMPAT_METADATA_CSUM))
+       if (!ext4_has_metadata_csum(sb))
                return 1;
 
        return es->s_checksum == ext4_superblock_csum(sb, es);
@@ -152,8 +150,7 @@ void ext4_superblock_csum_set(struct super_block *sb)
 {
        struct ext4_super_block *es = EXT4_SB(sb)->s_es;
 
-       if (!EXT4_HAS_RO_COMPAT_FEATURE(sb,
-               EXT4_FEATURE_RO_COMPAT_METADATA_CSUM))
+       if (!ext4_has_metadata_csum(sb))
                return;
 
        es->s_checksum = ext4_superblock_csum(sb, es);
@@ -1002,7 +999,7 @@ static struct inode *ext4_nfs_get_inode(struct super_block *sb,
         * Currently we don't know the generation for parent directory, so
         * a generation of 0 means "accept any"
         */
-       inode = ext4_iget(sb, ino);
+       inode = ext4_iget_normal(sb, ino);
        if (IS_ERR(inode))
                return ERR_CAST(inode);
        if (generation && inode->i_generation != generation) {
@@ -1124,25 +1121,6 @@ static const struct super_operations ext4_sops = {
        .bdev_try_to_free_page = bdev_try_to_free_page,
 };
 
-static const struct super_operations ext4_nojournal_sops = {
-       .alloc_inode    = ext4_alloc_inode,
-       .destroy_inode  = ext4_destroy_inode,
-       .write_inode    = ext4_write_inode,
-       .dirty_inode    = ext4_dirty_inode,
-       .drop_inode     = ext4_drop_inode,
-       .evict_inode    = ext4_evict_inode,
-       .sync_fs        = ext4_sync_fs_nojournal,
-       .put_super      = ext4_put_super,
-       .statfs         = ext4_statfs,
-       .remount_fs     = ext4_remount,
-       .show_options   = ext4_show_options,
-#ifdef CONFIG_QUOTA
-       .quota_read     = ext4_quota_read,
-       .quota_write    = ext4_quota_write,
-#endif
-       .bdev_try_to_free_page = bdev_try_to_free_page,
-};
-
 static const struct export_operations ext4_export_ops = {
        .fh_to_dentry = ext4_fh_to_dentry,
        .fh_to_parent = ext4_fh_to_parent,
@@ -1712,13 +1690,6 @@ static int parse_options(char *options, struct super_block *sb,
                                        "not specified");
                        return 0;
                }
-       } else {
-               if (sbi->s_jquota_fmt) {
-                       ext4_msg(sb, KERN_ERR, "journaled quota format "
-                                       "specified with no journaling "
-                                       "enabled");
-                       return 0;
-               }
        }
 #endif
        if (test_opt(sb, DIOREAD_NOLOCK)) {
@@ -2016,8 +1987,7 @@ static __le16 ext4_group_desc_csum(struct ext4_sb_info *sbi, __u32 block_group,
        __u16 crc = 0;
        __le32 le_group = cpu_to_le32(block_group);
 
-       if ((sbi->s_es->s_feature_ro_compat &
-            cpu_to_le32(EXT4_FEATURE_RO_COMPAT_METADATA_CSUM))) {
+       if (ext4_has_metadata_csum(sbi->s_sb)) {
                /* Use new metadata_csum algorithm */
                __le16 save_csum;
                __u32 csum32;
@@ -2191,7 +2161,7 @@ static void ext4_orphan_cleanup(struct super_block *sb,
        if (EXT4_SB(sb)->s_mount_state & EXT4_ERROR_FS) {
                /* don't clear list on RO mount w/ errors */
                if (es->s_last_orphan && !(s_flags & MS_RDONLY)) {
-                       jbd_debug(1, "Errors on filesystem, "
+                       ext4_msg(sb, KERN_INFO, "Errors on filesystem, "
                                  "clearing orphan list.\n");
                        es->s_last_orphan = 0;
                }
@@ -3226,8 +3196,7 @@ static int set_journal_csum_feature_set(struct super_block *sb)
        int compat, incompat;
        struct ext4_sb_info *sbi = EXT4_SB(sb);
 
-       if (EXT4_HAS_RO_COMPAT_FEATURE(sb,
-                                      EXT4_FEATURE_RO_COMPAT_METADATA_CSUM)) {
+       if (ext4_has_metadata_csum(sb)) {
                /* journal checksum v3 */
                compat = 0;
                incompat = JBD2_FEATURE_INCOMPAT_CSUM_V3;
@@ -3535,8 +3504,7 @@ static int ext4_fill_super(struct super_block *sb, void *data, int silent)
        }
 
        /* Precompute checksum seed for all metadata */
-       if (EXT4_HAS_RO_COMPAT_FEATURE(sb,
-                       EXT4_FEATURE_RO_COMPAT_METADATA_CSUM))
+       if (ext4_has_metadata_csum(sb))
                sbi->s_csum_seed = ext4_chksum(sbi, ~0, es->s_uuid,
                                               sizeof(es->s_uuid));
 
@@ -3947,11 +3915,7 @@ static int ext4_fill_super(struct super_block *sb, void *data, int silent)
        /*
         * set up enough so that it can read an inode
         */
-       if (!test_opt(sb, NOLOAD) &&
-           EXT4_HAS_COMPAT_FEATURE(sb, EXT4_FEATURE_COMPAT_HAS_JOURNAL))
-               sb->s_op = &ext4_sops;
-       else
-               sb->s_op = &ext4_nojournal_sops;
+       sb->s_op = &ext4_sops;
        sb->s_export_op = &ext4_export_ops;
        sb->s_xattr = ext4_xattr_handlers;
 #ifdef CONFIG_QUOTA
@@ -4414,6 +4378,15 @@ static journal_t *ext4_get_dev_journal(struct super_block *sb,
                goto out_bdev;
        }
 
+       if ((le32_to_cpu(es->s_feature_ro_compat) &
+            EXT4_FEATURE_RO_COMPAT_METADATA_CSUM) &&
+           es->s_checksum != ext4_superblock_csum(sb, es)) {
+               ext4_msg(sb, KERN_ERR, "external journal has "
+                                      "corrupt superblock");
+               brelse(bh);
+               goto out_bdev;
+       }
+
        if (memcmp(EXT4_SB(sb)->s_es->s_journal_uuid, es->s_uuid, 16)) {
                ext4_msg(sb, KERN_ERR, "journal UUID does not match");
                brelse(bh);
@@ -4716,15 +4689,19 @@ static int ext4_sync_fs(struct super_block *sb, int wait)
         * being sent at the end of the function. But we can skip it if
         * transaction_commit will do it for us.
         */
-       target = jbd2_get_latest_transaction(sbi->s_journal);
-       if (wait && sbi->s_journal->j_flags & JBD2_BARRIER &&
-           !jbd2_trans_will_send_data_barrier(sbi->s_journal, target))
+       if (sbi->s_journal) {
+               target = jbd2_get_latest_transaction(sbi->s_journal);
+               if (wait && sbi->s_journal->j_flags & JBD2_BARRIER &&
+                   !jbd2_trans_will_send_data_barrier(sbi->s_journal, target))
+                       needs_barrier = true;
+
+               if (jbd2_journal_start_commit(sbi->s_journal, &target)) {
+                       if (wait)
+                               ret = jbd2_log_wait_commit(sbi->s_journal,
+                                                          target);
+               }
+       } else if (wait && test_opt(sb, BARRIER))
                needs_barrier = true;
-
-       if (jbd2_journal_start_commit(sbi->s_journal, &target)) {
-               if (wait)
-                       ret = jbd2_log_wait_commit(sbi->s_journal, target);
-       }
        if (needs_barrier) {
                int err;
                err = blkdev_issue_flush(sb->s_bdev, GFP_KERNEL, NULL);
@@ -4735,19 +4712,6 @@ static int ext4_sync_fs(struct super_block *sb, int wait)
        return ret;
 }
 
-static int ext4_sync_fs_nojournal(struct super_block *sb, int wait)
-{
-       int ret = 0;
-
-       trace_ext4_sync_fs(sb, wait);
-       flush_workqueue(EXT4_SB(sb)->rsv_conversion_wq);
-       dquot_writeback_dquots(sb, -1);
-       if (wait && test_opt(sb, BARRIER))
-               ret = blkdev_issue_flush(sb->s_bdev, GFP_KERNEL, NULL);
-
-       return ret;
-}
-
 /*
  * LVM calls this function before a (read-only) snapshot is created.  This
  * gives us a chance to flush the journal completely and mark the fs clean.
@@ -4766,23 +4730,26 @@ static int ext4_freeze(struct super_block *sb)
 
        journal = EXT4_SB(sb)->s_journal;
 
-       /* Now we set up the journal barrier. */
-       jbd2_journal_lock_updates(journal);
+       if (journal) {
+               /* Now we set up the journal barrier. */
+               jbd2_journal_lock_updates(journal);
 
-       /*
-        * Don't clear the needs_recovery flag if we failed to flush
-        * the journal.
-        */
-       error = jbd2_journal_flush(journal);
-       if (error < 0)
-               goto out;
+               /*
+                * Don't clear the needs_recovery flag if we failed to
+                * flush the journal.
+                */
+               error = jbd2_journal_flush(journal);
+               if (error < 0)
+                       goto out;
+       }
 
        /* Journal blocked and flushed, clear needs_recovery flag. */
        EXT4_CLEAR_INCOMPAT_FEATURE(sb, EXT4_FEATURE_INCOMPAT_RECOVER);
        error = ext4_commit_super(sb, 1);
 out:
-       /* we rely on upper layer to stop further updates */
-       jbd2_journal_unlock_updates(EXT4_SB(sb)->s_journal);
+       if (journal)
+               /* we rely on upper layer to stop further updates */
+               jbd2_journal_unlock_updates(journal);
        return error;
 }