]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
5.4-stable patches
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 6 Jun 2022 11:40:18 +0000 (13:40 +0200)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 6 Jun 2022 11:40:18 +0000 (13:40 +0200)
added patches:
f2fs-don-t-need-inode-lock-for-system-hidden-quota.patch
f2fs-fix-deadloop-in-foreground-gc.patch
f2fs-fix-fallocate-to-use-file_modified-to-update-permissions-consistently.patch
f2fs-fix-to-clear-dirty-inode-in-f2fs_evict_inode.patch

queue-5.4/f2fs-don-t-need-inode-lock-for-system-hidden-quota.patch [new file with mode: 0644]
queue-5.4/f2fs-fix-deadloop-in-foreground-gc.patch [new file with mode: 0644]
queue-5.4/f2fs-fix-fallocate-to-use-file_modified-to-update-permissions-consistently.patch [new file with mode: 0644]
queue-5.4/f2fs-fix-to-clear-dirty-inode-in-f2fs_evict_inode.patch [new file with mode: 0644]
queue-5.4/series

diff --git a/queue-5.4/f2fs-don-t-need-inode-lock-for-system-hidden-quota.patch b/queue-5.4/f2fs-don-t-need-inode-lock-for-system-hidden-quota.patch
new file mode 100644 (file)
index 0000000..f881733
--- /dev/null
@@ -0,0 +1,90 @@
+From 6213f5d4d23c50d393a31dc8e351e63a1fd10dbe Mon Sep 17 00:00:00 2001
+From: Jaegeuk Kim <jaegeuk@kernel.org>
+Date: Thu, 5 May 2022 17:40:25 -0700
+Subject: f2fs: don't need inode lock for system hidden quota
+
+From: Jaegeuk Kim <jaegeuk@kernel.org>
+
+commit 6213f5d4d23c50d393a31dc8e351e63a1fd10dbe upstream.
+
+Let's avoid false-alarmed lockdep warning.
+
+[   58.914674] [T1501146] -> #2 (&sb->s_type->i_mutex_key#20){+.+.}-{3:3}:
+[   58.915975] [T1501146] system_server:        down_write+0x7c/0xe0
+[   58.916738] [T1501146] system_server:        f2fs_quota_sync+0x60/0x1a8
+[   58.917563] [T1501146] system_server:        block_operations+0x16c/0x43c
+[   58.918410] [T1501146] system_server:        f2fs_write_checkpoint+0x114/0x318
+[   58.919312] [T1501146] system_server:        f2fs_issue_checkpoint+0x178/0x21c
+[   58.920214] [T1501146] system_server:        f2fs_sync_fs+0x48/0x6c
+[   58.920999] [T1501146] system_server:        f2fs_do_sync_file+0x334/0x738
+[   58.921862] [T1501146] system_server:        f2fs_sync_file+0x30/0x48
+[   58.922667] [T1501146] system_server:        __arm64_sys_fsync+0x84/0xf8
+[   58.923506] [T1501146] system_server:        el0_svc_common.llvm.12821150825140585682+0xd8/0x20c
+[   58.924604] [T1501146] system_server:        do_el0_svc+0x28/0xa0
+[   58.925366] [T1501146] system_server:        el0_svc+0x24/0x38
+[   58.926094] [T1501146] system_server:        el0_sync_handler+0x88/0xec
+[   58.926920] [T1501146] system_server:        el0_sync+0x1b4/0x1c0
+
+[   58.927681] [T1501146] -> #1 (&sbi->cp_global_sem){+.+.}-{3:3}:
+[   58.928889] [T1501146] system_server:        down_write+0x7c/0xe0
+[   58.929650] [T1501146] system_server:        f2fs_write_checkpoint+0xbc/0x318
+[   58.930541] [T1501146] system_server:        f2fs_issue_checkpoint+0x178/0x21c
+[   58.931443] [T1501146] system_server:        f2fs_sync_fs+0x48/0x6c
+[   58.932226] [T1501146] system_server:        sync_filesystem+0xac/0x130
+[   58.933053] [T1501146] system_server:        generic_shutdown_super+0x38/0x150
+[   58.933958] [T1501146] system_server:        kill_block_super+0x24/0x58
+[   58.934791] [T1501146] system_server:        kill_f2fs_super+0xcc/0x124
+[   58.935618] [T1501146] system_server:        deactivate_locked_super+0x90/0x120
+[   58.936529] [T1501146] system_server:        deactivate_super+0x74/0xac
+[   58.937356] [T1501146] system_server:        cleanup_mnt+0x128/0x168
+[   58.938150] [T1501146] system_server:        __cleanup_mnt+0x18/0x28
+[   58.938944] [T1501146] system_server:        task_work_run+0xb8/0x14c
+[   58.939749] [T1501146] system_server:        do_notify_resume+0x114/0x1e8
+[   58.940595] [T1501146] system_server:        work_pending+0xc/0x5f0
+
+[   58.941375] [T1501146] -> #0 (&sbi->gc_lock){+.+.}-{3:3}:
+[   58.942519] [T1501146] system_server:        __lock_acquire+0x1270/0x2868
+[   58.943366] [T1501146] system_server:        lock_acquire+0x114/0x294
+[   58.944169] [T1501146] system_server:        down_write+0x7c/0xe0
+[   58.944930] [T1501146] system_server:        f2fs_issue_checkpoint+0x13c/0x21c
+[   58.945831] [T1501146] system_server:        f2fs_sync_fs+0x48/0x6c
+[   58.946614] [T1501146] system_server:        f2fs_do_sync_file+0x334/0x738
+[   58.947472] [T1501146] system_server:        f2fs_ioc_commit_atomic_write+0xc8/0x14c
+[   58.948439] [T1501146] system_server:        __f2fs_ioctl+0x674/0x154c
+[   58.949253] [T1501146] system_server:        f2fs_ioctl+0x54/0x88
+[   58.950018] [T1501146] system_server:        __arm64_sys_ioctl+0xa8/0x110
+[   58.950865] [T1501146] system_server:        el0_svc_common.llvm.12821150825140585682+0xd8/0x20c
+[   58.951965] [T1501146] system_server:        do_el0_svc+0x28/0xa0
+[   58.952727] [T1501146] system_server:        el0_svc+0x24/0x38
+[   58.953454] [T1501146] system_server:        el0_sync_handler+0x88/0xec
+[   58.954279] [T1501146] system_server:        el0_sync+0x1b4/0x1c0
+
+Cc: stable@vger.kernel.org
+Signed-off-by: Jaegeuk Kim <jaegeuk@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ fs/f2fs/super.c |    6 ++++--
+ 1 file changed, 4 insertions(+), 2 deletions(-)
+
+--- a/fs/f2fs/super.c
++++ b/fs/f2fs/super.c
+@@ -2080,7 +2080,8 @@ int f2fs_quota_sync(struct super_block *
+               if (!sb_has_quota_active(sb, cnt))
+                       continue;
+-              inode_lock(dqopt->files[cnt]);
++              if (!f2fs_sb_has_quota_ino(sbi))
++                      inode_lock(dqopt->files[cnt]);
+               /*
+                * do_quotactl
+@@ -2099,7 +2100,8 @@ int f2fs_quota_sync(struct super_block *
+               up_read(&sbi->quota_sem);
+               f2fs_unlock_op(sbi);
+-              inode_unlock(dqopt->files[cnt]);
++              if (!f2fs_sb_has_quota_ino(sbi))
++                      inode_unlock(dqopt->files[cnt]);
+               if (ret)
+                       break;
diff --git a/queue-5.4/f2fs-fix-deadloop-in-foreground-gc.patch b/queue-5.4/f2fs-fix-deadloop-in-foreground-gc.patch
new file mode 100644 (file)
index 0000000..7a3c323
--- /dev/null
@@ -0,0 +1,92 @@
+From cfd66bb715fd11fde3338d0660cffa1396adc27d Mon Sep 17 00:00:00 2001
+From: Chao Yu <chao@kernel.org>
+Date: Wed, 4 May 2022 14:09:22 +0800
+Subject: f2fs: fix deadloop in foreground GC
+
+From: Chao Yu <chao@kernel.org>
+
+commit cfd66bb715fd11fde3338d0660cffa1396adc27d upstream.
+
+As Yanming reported in bugzilla:
+
+https://bugzilla.kernel.org/show_bug.cgi?id=215914
+
+The root cause is: in a very small sized image, it's very easy to
+exceed threshold of foreground GC, if we calculate free space and
+dirty data based on section granularity, in corner case,
+has_not_enough_free_secs() will always return true, result in
+deadloop in f2fs_gc().
+
+So this patch refactors has_not_enough_free_secs() as below to fix
+this issue:
+1. calculate needed space based on block granularity, and separate
+all blocks to two parts, section part, and block part, comparing
+section part to free section, and comparing block part to free space
+in openned log.
+2. account F2FS_DIRTY_NODES, F2FS_DIRTY_IMETA and F2FS_DIRTY_DENTS
+as node block consumer;
+3. account F2FS_DIRTY_DENTS as data block consumer;
+
+Cc: stable@vger.kernel.org
+Reported-by: Ming Yan <yanming@tju.edu.cn>
+Signed-off-by: Chao Yu <chao.yu@oppo.com>
+Signed-off-by: Jaegeuk Kim <jaegeuk@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ fs/f2fs/segment.h |   32 ++++++++++++++++++++------------
+ 1 file changed, 20 insertions(+), 12 deletions(-)
+
+--- a/fs/f2fs/segment.h
++++ b/fs/f2fs/segment.h
+@@ -542,11 +542,10 @@ static inline int reserved_sections(stru
+       return GET_SEC_FROM_SEG(sbi, (unsigned int)reserved_segments(sbi));
+ }
+-static inline bool has_curseg_enough_space(struct f2fs_sb_info *sbi)
++static inline bool has_curseg_enough_space(struct f2fs_sb_info *sbi,
++                      unsigned int node_blocks, unsigned int dent_blocks)
+ {
+-      unsigned int node_blocks = get_pages(sbi, F2FS_DIRTY_NODES) +
+-                                      get_pages(sbi, F2FS_DIRTY_DENTS);
+-      unsigned int dent_blocks = get_pages(sbi, F2FS_DIRTY_DENTS);
++
+       unsigned int segno, left_blocks;
+       int i;
+@@ -572,19 +571,28 @@ static inline bool has_curseg_enough_spa
+ static inline bool has_not_enough_free_secs(struct f2fs_sb_info *sbi,
+                                       int freed, int needed)
+ {
+-      int node_secs = get_blocktype_secs(sbi, F2FS_DIRTY_NODES);
+-      int dent_secs = get_blocktype_secs(sbi, F2FS_DIRTY_DENTS);
+-      int imeta_secs = get_blocktype_secs(sbi, F2FS_DIRTY_IMETA);
++      unsigned int total_node_blocks = get_pages(sbi, F2FS_DIRTY_NODES) +
++                                      get_pages(sbi, F2FS_DIRTY_DENTS) +
++                                      get_pages(sbi, F2FS_DIRTY_IMETA);
++      unsigned int total_dent_blocks = get_pages(sbi, F2FS_DIRTY_DENTS);
++      unsigned int node_secs = total_node_blocks / BLKS_PER_SEC(sbi);
++      unsigned int dent_secs = total_dent_blocks / BLKS_PER_SEC(sbi);
++      unsigned int node_blocks = total_node_blocks % BLKS_PER_SEC(sbi);
++      unsigned int dent_blocks = total_dent_blocks % BLKS_PER_SEC(sbi);
++      unsigned int free, need_lower, need_upper;
+       if (unlikely(is_sbi_flag_set(sbi, SBI_POR_DOING)))
+               return false;
+-      if (free_sections(sbi) + freed == reserved_sections(sbi) + needed &&
+-                      has_curseg_enough_space(sbi))
++      free = free_sections(sbi) + freed;
++      need_lower = node_secs + dent_secs + reserved_sections(sbi) + needed;
++      need_upper = need_lower + (node_blocks ? 1 : 0) + (dent_blocks ? 1 : 0);
++
++      if (free > need_upper)
+               return false;
+-      return (free_sections(sbi) + freed) <=
+-              (node_secs + 2 * dent_secs + imeta_secs +
+-              reserved_sections(sbi) + needed);
++      else if (free <= need_lower)
++              return true;
++      return !has_curseg_enough_space(sbi, node_blocks, dent_blocks);
+ }
+ static inline bool f2fs_is_checkpoint_ready(struct f2fs_sb_info *sbi)
diff --git a/queue-5.4/f2fs-fix-fallocate-to-use-file_modified-to-update-permissions-consistently.patch b/queue-5.4/f2fs-fix-fallocate-to-use-file_modified-to-update-permissions-consistently.patch
new file mode 100644 (file)
index 0000000..6503ca4
--- /dev/null
@@ -0,0 +1,44 @@
+From 958ed92922028ec67f504dcdc72bfdfd0f43936a Mon Sep 17 00:00:00 2001
+From: Chao Yu <chao@kernel.org>
+Date: Tue, 17 May 2022 11:37:23 +0800
+Subject: f2fs: fix fallocate to use file_modified to update permissions consistently
+
+From: Chao Yu <chao@kernel.org>
+
+commit 958ed92922028ec67f504dcdc72bfdfd0f43936a upstream.
+
+This patch tries to fix permission consistency issue as all other
+mainline filesystems.
+
+Since the initial introduction of (posix) fallocate back at the turn of
+the century, it has been possible to use this syscall to change the
+user-visible contents of files.  This can happen by extending the file
+size during a preallocation, or through any of the newer modes (punch,
+zero, collapse, insert range).  Because the call can be used to change
+file contents, we should treat it like we do any other modification to a
+file -- update the mtime, and drop set[ug]id privileges/capabilities.
+
+The VFS function file_modified() does all this for us if pass it a
+locked inode, so let's make fallocate drop permissions correctly.
+
+Cc: stable@kernel.org
+Signed-off-by: Chao Yu <chao.yu@oppo.com>
+Signed-off-by: Jaegeuk Kim <jaegeuk@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ fs/f2fs/file.c |    4 ++++
+ 1 file changed, 4 insertions(+)
+
+--- a/fs/f2fs/file.c
++++ b/fs/f2fs/file.c
+@@ -1608,6 +1608,10 @@ static long f2fs_fallocate(struct file *
+       inode_lock(inode);
++      ret = file_modified(file);
++      if (ret)
++              goto out;
++
+       if (mode & FALLOC_FL_PUNCH_HOLE) {
+               if (offset >= inode->i_size)
+                       goto out;
diff --git a/queue-5.4/f2fs-fix-to-clear-dirty-inode-in-f2fs_evict_inode.patch b/queue-5.4/f2fs-fix-to-clear-dirty-inode-in-f2fs_evict_inode.patch
new file mode 100644 (file)
index 0000000..ac06975
--- /dev/null
@@ -0,0 +1,79 @@
+From f2db71053dc0409fae785096ad19cce4c8a95af7 Mon Sep 17 00:00:00 2001
+From: Chao Yu <chao@kernel.org>
+Date: Sat, 30 Apr 2022 21:19:24 +0800
+Subject: f2fs: fix to clear dirty inode in f2fs_evict_inode()
+
+From: Chao Yu <chao@kernel.org>
+
+commit f2db71053dc0409fae785096ad19cce4c8a95af7 upstream.
+
+As Yanming reported in bugzilla:
+
+https://bugzilla.kernel.org/show_bug.cgi?id=215904
+
+The kernel message is shown below:
+
+kernel BUG at fs/f2fs/inode.c:825!
+Call Trace:
+ evict+0x282/0x4e0
+ __dentry_kill+0x2b2/0x4d0
+ shrink_dentry_list+0x17c/0x4f0
+ shrink_dcache_parent+0x143/0x1e0
+ do_one_tree+0x9/0x30
+ shrink_dcache_for_umount+0x51/0x120
+ generic_shutdown_super+0x5c/0x3a0
+ kill_block_super+0x90/0xd0
+ kill_f2fs_super+0x225/0x310
+ deactivate_locked_super+0x78/0xc0
+ cleanup_mnt+0x2b7/0x480
+ task_work_run+0xc8/0x150
+ exit_to_user_mode_prepare+0x14a/0x150
+ syscall_exit_to_user_mode+0x1d/0x40
+ do_syscall_64+0x48/0x90
+
+The root cause is: inode node and dnode node share the same nid,
+so during f2fs_evict_inode(), dnode node truncation will invalidate
+its NAT entry, so when truncating inode node, it fails due to
+invalid NAT entry, result in inode is still marked as dirty, fix
+this issue by clearing dirty for inode and setting SBI_NEED_FSCK
+flag in filesystem.
+
+output from dump.f2fs:
+[print_node_info: 354] Node ID [0xf:15] is inode
+i_nid[0]                               [0x       f : 15]
+
+Cc: stable@vger.kernel.org
+Reported-by: Ming Yan <yanming@tju.edu.cn>
+Signed-off-by: Chao Yu <chao.yu@oppo.com>
+Signed-off-by: Jaegeuk Kim <jaegeuk@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ fs/f2fs/inode.c |   16 +++++++++++++++-
+ 1 file changed, 15 insertions(+), 1 deletion(-)
+
+--- a/fs/f2fs/inode.c
++++ b/fs/f2fs/inode.c
+@@ -689,8 +689,22 @@ retry:
+               f2fs_lock_op(sbi);
+               err = f2fs_remove_inode_page(inode);
+               f2fs_unlock_op(sbi);
+-              if (err == -ENOENT)
++              if (err == -ENOENT) {
+                       err = 0;
++
++                      /*
++                       * in fuzzed image, another node may has the same
++                       * block address as inode's, if it was truncated
++                       * previously, truncation of inode node will fail.
++                       */
++                      if (is_inode_flag_set(inode, FI_DIRTY_INODE)) {
++                              f2fs_warn(F2FS_I_SB(inode),
++                                      "f2fs_evict_inode: inconsistent node id, ino:%lu",
++                                      inode->i_ino);
++                              f2fs_inode_synced(inode);
++                              set_sbi_flag(sbi, SBI_NEED_FSCK);
++                      }
++              }
+       }
+       /* give more chances, if ENOMEM case */
index e7293b3ad21049c4c85143f447c4e84c094d3526..cd03b25c271becdfa9c164c5391e4b7b4ed8014a 100644 (file)
@@ -209,3 +209,7 @@ perf-c2c-use-stdio-interface-if-slang-is-not-support.patch
 perf-jevents-fix-event-syntax-error-caused-by-extsel.patch
 f2fs-fix-to-avoid-f2fs_bug_on-in-dec_valid_node_count.patch
 f2fs-fix-to-do-sanity-check-on-block-address-in-f2fs_do_zero_range.patch
+f2fs-fix-to-clear-dirty-inode-in-f2fs_evict_inode.patch
+f2fs-fix-deadloop-in-foreground-gc.patch
+f2fs-don-t-need-inode-lock-for-system-hidden-quota.patch
+f2fs-fix-fallocate-to-use-file_modified-to-update-permissions-consistently.patch