From 0c67f997739732db2a0216c594c3878cebc0e51a Mon Sep 17 00:00:00 2001 From: Greg Kroah-Hartman Date: Wed, 22 Aug 2018 11:11:26 +0200 Subject: [PATCH] 4.14-stable patches added patches: f2fs-return-error-during-fill_super.patch f2fs-sanity-check-for-total-valid-node-blocks.patch kvm-irqfd-fix-race-between-epollhup-and-irq_bypass_register_consumer.patch --- .../f2fs-return-error-during-fill_super.patch | 120 ++++++++++++++ ...ty-check-for-total-valid-node-blocks.patch | 147 ++++++++++++++++++ ...hup-and-irq_bypass_register_consumer.patch | 51 ++++++ queue-4.14/series | 3 + 4 files changed, 321 insertions(+) create mode 100644 queue-4.14/f2fs-return-error-during-fill_super.patch create mode 100644 queue-4.14/f2fs-sanity-check-for-total-valid-node-blocks.patch create mode 100644 queue-4.14/kvm-irqfd-fix-race-between-epollhup-and-irq_bypass_register_consumer.patch diff --git a/queue-4.14/f2fs-return-error-during-fill_super.patch b/queue-4.14/f2fs-return-error-during-fill_super.patch new file mode 100644 index 00000000000..611253aeee6 --- /dev/null +++ b/queue-4.14/f2fs-return-error-during-fill_super.patch @@ -0,0 +1,120 @@ +From c39a1b348c4fe172729eff77c533dabc3c7cdaa7 Mon Sep 17 00:00:00 2001 +From: Jaegeuk Kim +Date: Tue, 19 Dec 2017 19:16:34 -0800 +Subject: f2fs: return error during fill_super + +From: Jaegeuk Kim + +commit c39a1b348c4fe172729eff77c533dabc3c7cdaa7 upstream. + +Let's avoid BUG_ON during fill_super, when on-disk was totall corrupted. + +Reviewed-by: Chao Yu +Signed-off-by: Jaegeuk Kim +Signed-off-by: Sudip Mukherjee +Signed-off-by: Greg Kroah-Hartman +--- + fs/f2fs/segment.c | 16 ++++++++++++---- + fs/f2fs/segment.h | 22 ++++++++++++++++++---- + 2 files changed, 30 insertions(+), 8 deletions(-) + +--- a/fs/f2fs/segment.c ++++ b/fs/f2fs/segment.c +@@ -3240,7 +3240,7 @@ static int build_curseg(struct f2fs_sb_i + return restore_curseg_summaries(sbi); + } + +-static void build_sit_entries(struct f2fs_sb_info *sbi) ++static int build_sit_entries(struct f2fs_sb_info *sbi) + { + struct sit_info *sit_i = SIT_I(sbi); + struct curseg_info *curseg = CURSEG_I(sbi, CURSEG_COLD_DATA); +@@ -3250,6 +3250,7 @@ static void build_sit_entries(struct f2f + int sit_blk_cnt = SIT_BLK_CNT(sbi); + unsigned int i, start, end; + unsigned int readed, start_blk = 0; ++ int err = 0; + + do { + readed = ra_meta_pages(sbi, start_blk, BIO_MAX_PAGES, +@@ -3268,7 +3269,9 @@ static void build_sit_entries(struct f2f + sit = sit_blk->entries[SIT_ENTRY_OFFSET(sit_i, start)]; + f2fs_put_page(page, 1); + +- check_block_count(sbi, start, &sit); ++ err = check_block_count(sbi, start, &sit); ++ if (err) ++ return err; + seg_info_from_raw_sit(se, &sit); + + /* build discard map only one time */ +@@ -3303,7 +3306,9 @@ static void build_sit_entries(struct f2f + + old_valid_blocks = se->valid_blocks; + +- check_block_count(sbi, start, &sit); ++ err = check_block_count(sbi, start, &sit); ++ if (err) ++ break; + seg_info_from_raw_sit(se, &sit); + + if (f2fs_discard_en(sbi)) { +@@ -3323,6 +3328,7 @@ static void build_sit_entries(struct f2f + se->valid_blocks - old_valid_blocks; + } + up_read(&curseg->journal_rwsem); ++ return err; + } + + static void init_free_segmap(struct f2fs_sb_info *sbi) +@@ -3492,7 +3498,9 @@ int build_segment_manager(struct f2fs_sb + return err; + + /* reinit free segmap based on SIT */ +- build_sit_entries(sbi); ++ err = build_sit_entries(sbi); ++ if (err) ++ return err; + + init_free_segmap(sbi); + err = build_dirty_segmap(sbi); +--- a/fs/f2fs/segment.h ++++ b/fs/f2fs/segment.h +@@ -625,7 +625,7 @@ static inline void verify_block_addr(str + /* + * Summary block is always treated as an invalid block + */ +-static inline void check_block_count(struct f2fs_sb_info *sbi, ++static inline int check_block_count(struct f2fs_sb_info *sbi, + int segno, struct f2fs_sit_entry *raw_sit) + { + #ifdef CONFIG_F2FS_CHECK_FS +@@ -647,11 +647,25 @@ static inline void check_block_count(str + cur_pos = next_pos; + is_valid = !is_valid; + } while (cur_pos < sbi->blocks_per_seg); +- BUG_ON(GET_SIT_VBLOCKS(raw_sit) != valid_blocks); ++ ++ if (unlikely(GET_SIT_VBLOCKS(raw_sit) != valid_blocks)) { ++ f2fs_msg(sbi->sb, KERN_ERR, ++ "Mismatch valid blocks %d vs. %d", ++ GET_SIT_VBLOCKS(raw_sit), valid_blocks); ++ set_sbi_flag(sbi, SBI_NEED_FSCK); ++ return -EINVAL; ++ } + #endif + /* check segment usage, and check boundary of a given segment number */ +- f2fs_bug_on(sbi, GET_SIT_VBLOCKS(raw_sit) > sbi->blocks_per_seg +- || segno > TOTAL_SEGS(sbi) - 1); ++ if (unlikely(GET_SIT_VBLOCKS(raw_sit) > sbi->blocks_per_seg ++ || segno > TOTAL_SEGS(sbi) - 1)) { ++ f2fs_msg(sbi->sb, KERN_ERR, ++ "Wrong valid blocks %d or segno %u", ++ GET_SIT_VBLOCKS(raw_sit), segno); ++ set_sbi_flag(sbi, SBI_NEED_FSCK); ++ return -EINVAL; ++ } ++ return 0; + } + + static inline pgoff_t current_sit_addr(struct f2fs_sb_info *sbi, diff --git a/queue-4.14/f2fs-sanity-check-for-total-valid-node-blocks.patch b/queue-4.14/f2fs-sanity-check-for-total-valid-node-blocks.patch new file mode 100644 index 00000000000..a49d6d32577 --- /dev/null +++ b/queue-4.14/f2fs-sanity-check-for-total-valid-node-blocks.patch @@ -0,0 +1,147 @@ +From 8a29c1260e24e7c9c6ab138aa0017558d8b28208 Mon Sep 17 00:00:00 2001 +From: Jaegeuk Kim +Date: Tue, 24 Apr 2018 21:34:05 -0600 +Subject: f2fs: sanity check for total valid node blocks + +From: Jaegeuk Kim + +commit 8a29c1260e24e7c9c6ab138aa0017558d8b28208 upstream. + +This patch enhances sanity check for SIT entries. + +syzbot hit the following crash on upstream commit +83beed7b2b26f232d782127792dd0cd4362fdc41 (Fri Apr 20 17:56:32 2018 +0000) +Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/evalenti/linux-soc-thermal +syzbot dashboard link: https://syzkaller.appspot.com/bug?extid=bf9253040425feb155ad + +syzkaller reproducer: https://syzkaller.appspot.com/x/repro.syz?id=5692130282438656 +Raw console output: https://syzkaller.appspot.com/x/log.txt?id=5095924598571008 +Kernel config: https://syzkaller.appspot.com/x/.config?id=1808800213120130118 +compiler: gcc (GCC) 8.0.1 20180413 (experimental) + +IMPORTANT: if you fix the bug, please add the following tag to the commit: +Reported-by: syzbot+bf9253040425feb155ad@syzkaller.appspotmail.com +It will help syzbot understand when the bug is fixed. See footer for details. +If you forward the report, please keep this part and the footer. + +F2FS-fs (loop0): invalid crc value +F2FS-fs (loop0): Try to recover 1th superblock, ret: 0 +F2FS-fs (loop0): Mounted with checkpoint version = d +F2FS-fs (loop0): Bitmap was wrongly cleared, blk:9740 +------------[ cut here ]------------ +kernel BUG at fs/f2fs/segment.c:1884! +invalid opcode: 0000 [#1] SMP KASAN +Dumping ftrace buffer: + (ftrace buffer empty) +Modules linked in: +CPU: 1 PID: 4508 Comm: syz-executor0 Not tainted 4.17.0-rc1+ #10 +Hardware name: Google Google Compute Engine/Google Compute Engine, BIOS Google 01/01/2011 +RIP: 0010:update_sit_entry+0x1215/0x1590 fs/f2fs/segment.c:1882 +RSP: 0018:ffff8801af526708 EFLAGS: 00010282 +RAX: ffffed0035ea4cc0 RBX: ffff8801ad454f90 RCX: 0000000000000000 +RDX: 0000000000000000 RSI: ffffffff82eeb87e RDI: ffffed0035ea4cb6 +RBP: ffff8801af526760 R08: ffff8801ad4a2480 R09: ffffed003b5e4f90 +R10: ffffed003b5e4f90 R11: ffff8801daf27c87 R12: ffff8801adb8d380 +R13: 0000000000000001 R14: 0000000000000008 R15: 00000000ffffffff +FS: 00000000014af940(0000) GS:ffff8801daf00000(0000) knlGS:0000000000000000 +CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 +CR2: 00007f06bc223000 CR3: 00000001adb02000 CR4: 00000000001406e0 +DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 +DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400 +Call Trace: + allocate_data_block+0x66f/0x2050 fs/f2fs/segment.c:2663 + do_write_page+0x105/0x1b0 fs/f2fs/segment.c:2727 + write_node_page+0x129/0x350 fs/f2fs/segment.c:2770 + __write_node_page+0x7da/0x1370 fs/f2fs/node.c:1398 + sync_node_pages+0x18cf/0x1eb0 fs/f2fs/node.c:1652 + block_operations+0x429/0xa60 fs/f2fs/checkpoint.c:1088 + write_checkpoint+0x3ba/0x5380 fs/f2fs/checkpoint.c:1405 + f2fs_sync_fs+0x2fb/0x6a0 fs/f2fs/super.c:1077 + __sync_filesystem fs/sync.c:39 [inline] + sync_filesystem+0x265/0x310 fs/sync.c:67 + generic_shutdown_super+0xd7/0x520 fs/super.c:429 + kill_block_super+0xa4/0x100 fs/super.c:1191 + kill_f2fs_super+0x9f/0xd0 fs/f2fs/super.c:3030 + deactivate_locked_super+0x97/0x100 fs/super.c:316 + deactivate_super+0x188/0x1b0 fs/super.c:347 + cleanup_mnt+0xbf/0x160 fs/namespace.c:1174 + __cleanup_mnt+0x16/0x20 fs/namespace.c:1181 + task_work_run+0x1e4/0x290 kernel/task_work.c:113 + tracehook_notify_resume include/linux/tracehook.h:191 [inline] + exit_to_usermode_loop+0x2bd/0x310 arch/x86/entry/common.c:166 + prepare_exit_to_usermode arch/x86/entry/common.c:196 [inline] + syscall_return_slowpath arch/x86/entry/common.c:265 [inline] + do_syscall_64+0x6ac/0x800 arch/x86/entry/common.c:290 + entry_SYSCALL_64_after_hwframe+0x49/0xbe +RIP: 0033:0x457d97 +RSP: 002b:00007ffd46f9c8e8 EFLAGS: 00000246 ORIG_RAX: 00000000000000a6 +RAX: 0000000000000000 RBX: 0000000000000000 RCX: 0000000000457d97 +RDX: 00000000014b09a3 RSI: 0000000000000002 RDI: 00007ffd46f9da50 +RBP: 00007ffd46f9da50 R08: 0000000000000000 R09: 0000000000000009 +R10: 0000000000000005 R11: 0000000000000246 R12: 00000000014b0940 +R13: 0000000000000000 R14: 0000000000000002 R15: 000000000000658e +RIP: update_sit_entry+0x1215/0x1590 fs/f2fs/segment.c:1882 RSP: ffff8801af526708 +---[ end trace f498328bb02610a2 ]--- + +Reported-and-tested-by: syzbot+bf9253040425feb155ad@syzkaller.appspotmail.com +Reported-and-tested-by: syzbot+7d6d31d3bc702f566ce3@syzkaller.appspotmail.com +Reported-and-tested-by: syzbot+0a725420475916460f12@syzkaller.appspotmail.com +Reviewed-by: Chao Yu +Signed-off-by: Jaegeuk Kim +Signed-off-by: Sudip Mukherjee +Signed-off-by: Greg Kroah-Hartman +--- + fs/f2fs/segment.c | 16 ++++++++++++++++ + 1 file changed, 16 insertions(+) + +--- a/fs/f2fs/segment.c ++++ b/fs/f2fs/segment.c +@@ -3251,6 +3251,7 @@ static int build_sit_entries(struct f2fs + unsigned int i, start, end; + unsigned int readed, start_blk = 0; + int err = 0; ++ block_t total_node_blocks = 0; + + do { + readed = ra_meta_pages(sbi, start_blk, BIO_MAX_PAGES, +@@ -3273,6 +3274,8 @@ static int build_sit_entries(struct f2fs + if (err) + return err; + seg_info_from_raw_sit(se, &sit); ++ if (IS_NODESEG(se->type)) ++ total_node_blocks += se->valid_blocks; + + /* build discard map only one time */ + if (f2fs_discard_en(sbi)) { +@@ -3305,11 +3308,15 @@ static int build_sit_entries(struct f2fs + sit = sit_in_journal(journal, i); + + old_valid_blocks = se->valid_blocks; ++ if (IS_NODESEG(se->type)) ++ total_node_blocks -= old_valid_blocks; + + err = check_block_count(sbi, start, &sit); + if (err) + break; + seg_info_from_raw_sit(se, &sit); ++ if (IS_NODESEG(se->type)) ++ total_node_blocks += se->valid_blocks; + + if (f2fs_discard_en(sbi)) { + if (is_set_ckpt_flags(sbi, CP_TRIMMED_FLAG)) { +@@ -3328,6 +3335,15 @@ static int build_sit_entries(struct f2fs + se->valid_blocks - old_valid_blocks; + } + up_read(&curseg->journal_rwsem); ++ ++ if (!err && total_node_blocks != valid_node_count(sbi)) { ++ f2fs_msg(sbi->sb, KERN_ERR, ++ "SIT is corrupted node# %u vs %u", ++ total_node_blocks, valid_node_count(sbi)); ++ set_sbi_flag(sbi, SBI_NEED_FSCK); ++ err = -EINVAL; ++ } ++ + return err; + } + diff --git a/queue-4.14/kvm-irqfd-fix-race-between-epollhup-and-irq_bypass_register_consumer.patch b/queue-4.14/kvm-irqfd-fix-race-between-epollhup-and-irq_bypass_register_consumer.patch new file mode 100644 index 00000000000..e1d0e9225af --- /dev/null +++ b/queue-4.14/kvm-irqfd-fix-race-between-epollhup-and-irq_bypass_register_consumer.patch @@ -0,0 +1,51 @@ +From 9432a3175770e06cb83eada2d91fac90c977cb99 Mon Sep 17 00:00:00 2001 +From: Paolo Bonzini +Date: Mon, 28 May 2018 13:31:13 +0200 +Subject: KVM: irqfd: fix race between EPOLLHUP and irq_bypass_register_consumer + +From: Paolo Bonzini + +commit 9432a3175770e06cb83eada2d91fac90c977cb99 upstream. + +A comment warning against this bug is there, but the code is not doing what +the comment says. Therefore it is possible that an EPOLLHUP races against +irq_bypass_register_consumer. The EPOLLHUP handler schedules irqfd_shutdown, +and if that runs soon enough, you get a use-after-free. + +Reported-by: syzbot +Cc: stable@vger.kernel.org +Signed-off-by: Paolo Bonzini +Reviewed-by: David Hildenbrand +Signed-off-by: Sudip Mukherjee +Signed-off-by: Greg Kroah-Hartman +--- + virt/kvm/eventfd.c | 11 ++++++----- + 1 file changed, 6 insertions(+), 5 deletions(-) + +--- a/virt/kvm/eventfd.c ++++ b/virt/kvm/eventfd.c +@@ -405,11 +405,6 @@ kvm_irqfd_assign(struct kvm *kvm, struct + if (events & POLLIN) + schedule_work(&irqfd->inject); + +- /* +- * do not drop the file until the irqfd is fully initialized, otherwise +- * we might race against the POLLHUP +- */ +- fdput(f); + #ifdef CONFIG_HAVE_KVM_IRQ_BYPASS + if (kvm_arch_has_irq_bypass()) { + irqfd->consumer.token = (void *)irqfd->eventfd; +@@ -425,6 +420,12 @@ kvm_irqfd_assign(struct kvm *kvm, struct + #endif + + srcu_read_unlock(&kvm->irq_srcu, idx); ++ ++ /* ++ * do not drop the file until the irqfd is fully initialized, otherwise ++ * we might race against the POLLHUP ++ */ ++ fdput(f); + return 0; + + fail: diff --git a/queue-4.14/series b/queue-4.14/series index 74b65a9e946..ca2b5027a2c 100644 --- a/queue-4.14/series +++ b/queue-4.14/series @@ -198,3 +198,6 @@ soc-imx-gpc-restrict-register-range-for-regmap-access.patch acpi-ec-use-ec_no_wakeup-on-more-thinkpad-x1-carbon-6th-systems.patch arm-dts-imx6-rdu2-fix-irq-type-for-mv88e6xxx-switch.patch nvme-fix-handling-of-metadata_len-for-nvme_ioctl_io_cmd.patch +kvm-irqfd-fix-race-between-epollhup-and-irq_bypass_register_consumer.patch +f2fs-return-error-during-fill_super.patch +f2fs-sanity-check-for-total-valid-node-blocks.patch -- 2.47.3