This patch add a new mount option "errors_mode" to adjust fs disposing cp error policy. Now supports "panic", "remount-ro", and "continue".
Signed-off-by: Yunlei He <heyun...@huawei.com> --- Documentation/filesystems/f2fs.txt | 2 ++ fs/f2fs/checkpoint.c | 11 +++++++++++ fs/f2fs/f2fs.h | 7 +++++++ fs/f2fs/super.c | 32 ++++++++++++++++++++++++++++++++ 4 files changed, 52 insertions(+) diff --git a/Documentation/filesystems/f2fs.txt b/Documentation/filesystems/f2fs.txt index 69f8de9..4a3493e 100644 --- a/Documentation/filesystems/f2fs.txt +++ b/Documentation/filesystems/f2fs.txt @@ -191,6 +191,8 @@ fsync_mode=%s Control the policy of fsync. Currently supports "posix", pass, but the performance will regress. "nobarrier" is based on "posix", but doesn't issue flush command for non-atomic files likewise "nobarrier" mount option. +errors_mode=%s Adjust fs disposing cp error policy. Now supports "panic", + "remount-ro", and "continue". test_dummy_encryption Enable dummy encryption, which provides a fake fscrypt context. The fake fscrypt context is used by xfstests. diff --git a/fs/f2fs/checkpoint.c b/fs/f2fs/checkpoint.c index 9c29526..36f6146 100644 --- a/fs/f2fs/checkpoint.c +++ b/fs/f2fs/checkpoint.c @@ -28,8 +28,19 @@ void f2fs_stop_checkpoint(struct f2fs_sb_info *sbi, bool end_io) { + int errors_mode = F2FS_OPTION(sbi).errors_mode; + f2fs_build_fault_attr(sbi, 0); set_ckpt_flags(sbi, CP_ERROR_FLAG); + if (errors_mode == ERRORS_MODE_PANIC) { + panic("F2FS-fs (device %s): panic forced after error\n", + sbi->sb->s_id); + } else if (errors_mode == ERRORS_MODE_REMOUNT_RO) { + f2fs_msg(sbi->sb, KERN_CRIT, + "Remounting filesystem read-only"); + sbi->sb->s_flags |= SB_RDONLY; + } + if (!end_io) f2fs_flush_merged_writes(sbi); } diff --git a/fs/f2fs/f2fs.h b/fs/f2fs/f2fs.h index 57a8851..1858cfb 100644 --- a/fs/f2fs/f2fs.h +++ b/fs/f2fs/f2fs.h @@ -133,6 +133,7 @@ struct f2fs_mount_info { int whint_mode; int alloc_mode; /* segment allocation policy */ int fsync_mode; /* fsync policy */ + int errors_mode; /* fs errors policy */ bool test_dummy_encryption; /* test dummy encryption */ }; @@ -1104,6 +1105,12 @@ enum fsync_mode { FSYNC_MODE_NOBARRIER, /* fsync behaves nobarrier based on posix */ }; +enum errors_mode { + ERRORS_MODE_PANIC, /* panic if cp error */ + ERRORS_MODE_REMOUNT_RO, /* remount-ro if cp error */ + ERRORS_MODE_CONTINUE, /* continue to run */ +}; + #ifdef CONFIG_F2FS_FS_ENCRYPTION #define DUMMY_ENCRYPTION_ENABLED(sbi) \ (unlikely(F2FS_OPTION(sbi).test_dummy_encryption)) diff --git a/fs/f2fs/super.c b/fs/f2fs/super.c index 7187885..feb43d7 100644 --- a/fs/f2fs/super.c +++ b/fs/f2fs/super.c @@ -131,6 +131,7 @@ enum { Opt_whint, Opt_alloc, Opt_fsync, + Opt_errors, Opt_test_dummy_encryption, Opt_err, }; @@ -188,6 +189,7 @@ enum { {Opt_whint, "whint_mode=%s"}, {Opt_alloc, "alloc_mode=%s"}, {Opt_fsync, "fsync_mode=%s"}, + {Opt_errors, "errors_mode=%s"}, {Opt_test_dummy_encryption, "test_dummy_encryption"}, {Opt_err, NULL}, }; @@ -749,6 +751,28 @@ static int parse_options(struct super_block *sb, char *options) } kfree(name); break; + case Opt_errors: + name = match_strdup(&args[0]); + if (!name) + return -ENOMEM; + if (strlen(name) == 5 && + !strncmp(name, "panic", 5)) { + F2FS_OPTION(sbi).errors_mode = + ERRORS_MODE_PANIC; + } else if (strlen(name) == 10 && + !strncmp(name, "remount-ro", 10)) { + F2FS_OPTION(sbi).errors_mode = + ERRORS_MODE_REMOUNT_RO; + } else if (strlen(name) == 8 && + !strncmp(name, "continue", 8)) { + F2FS_OPTION(sbi).errors_mode = + ERRORS_MODE_CONTINUE; + } else { + kfree(name); + return -EINVAL; + } + kfree(name); + break; case Opt_test_dummy_encryption: #ifdef CONFIG_F2FS_FS_ENCRYPTION if (!f2fs_sb_has_encrypt(sb)) { @@ -1344,6 +1368,13 @@ static int f2fs_show_options(struct seq_file *seq, struct dentry *root) seq_printf(seq, ",fsync_mode=%s", "strict"); else if (F2FS_OPTION(sbi).fsync_mode == FSYNC_MODE_NOBARRIER) seq_printf(seq, ",fsync_mode=%s", "nobarrier"); + + if (F2FS_OPTION(sbi).errors_mode == ERRORS_MODE_PANIC) + seq_printf(seq, ",errors_mode=%s", "panic"); + else if (F2FS_OPTION(sbi).errors_mode == ERRORS_MODE_REMOUNT_RO) + seq_printf(seq, ",errors_mode=%s", "remount-ro"); + else if (F2FS_OPTION(sbi).errors_mode == ERRORS_MODE_CONTINUE) + seq_printf(seq, ",errors_mode=%s", "continue"); return 0; } @@ -1355,6 +1386,7 @@ static void default_options(struct f2fs_sb_info *sbi) F2FS_OPTION(sbi).whint_mode = WHINT_MODE_OFF; F2FS_OPTION(sbi).alloc_mode = ALLOC_MODE_DEFAULT; F2FS_OPTION(sbi).fsync_mode = FSYNC_MODE_POSIX; + F2FS_OPTION(sbi).errors_mode = ERRORS_MODE_CONTINUE; F2FS_OPTION(sbi).test_dummy_encryption = false; F2FS_OPTION(sbi).s_resuid = make_kuid(&init_user_ns, F2FS_DEF_RESUID); F2FS_OPTION(sbi).s_resgid = make_kgid(&init_user_ns, F2FS_DEF_RESGID); -- 1.9.1 ------------------------------------------------------------------------------ Check out the vibrant tech community on one of the world's most engaging tech sites, Slashdot.org! http://sdm.link/slashdot _______________________________________________ Linux-f2fs-devel mailing list Linux-f2fs-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/linux-f2fs-devel