]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
5.15-stable patches
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Sun, 18 Feb 2024 09:41:26 +0000 (10:41 +0100)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Sun, 18 Feb 2024 09:41:26 +0000 (10:41 +0100)
added patches:
btrfs-do-not-assert-if-the-newly-created-subvolume-already-got-read.patch
btrfs-forbid-creating-subvol-qgroups.patch
btrfs-forbid-deleting-live-subvol-qgroup.patch
btrfs-send-return-eopnotsupp-on-unknown-flags.patch

queue-5.15/btrfs-do-not-assert-if-the-newly-created-subvolume-already-got-read.patch [new file with mode: 0644]
queue-5.15/btrfs-forbid-creating-subvol-qgroups.patch [new file with mode: 0644]
queue-5.15/btrfs-forbid-deleting-live-subvol-qgroup.patch [new file with mode: 0644]
queue-5.15/btrfs-send-return-eopnotsupp-on-unknown-flags.patch [new file with mode: 0644]
queue-5.15/series

diff --git a/queue-5.15/btrfs-do-not-assert-if-the-newly-created-subvolume-already-got-read.patch b/queue-5.15/btrfs-do-not-assert-if-the-newly-created-subvolume-already-got-read.patch
new file mode 100644 (file)
index 0000000..19e4b9d
--- /dev/null
@@ -0,0 +1,92 @@
+From e03ee2fe873eb68c1f9ba5112fee70303ebf9dfb Mon Sep 17 00:00:00 2001
+From: Qu Wenruo <wqu@suse.com>
+Date: Sat, 20 Jan 2024 19:41:28 +1030
+Subject: btrfs: do not ASSERT() if the newly created subvolume already got read
+
+From: Qu Wenruo <wqu@suse.com>
+
+commit e03ee2fe873eb68c1f9ba5112fee70303ebf9dfb upstream.
+
+[BUG]
+There is a syzbot crash, triggered by the ASSERT() during subvolume
+creation:
+
+ assertion failed: !anon_dev, in fs/btrfs/disk-io.c:1319
+ ------------[ cut here ]------------
+ kernel BUG at fs/btrfs/disk-io.c:1319!
+ invalid opcode: 0000 [#1] PREEMPT SMP KASAN
+ RIP: 0010:btrfs_get_root_ref.part.0+0x9aa/0xa60
+  <TASK>
+  btrfs_get_new_fs_root+0xd3/0xf0
+  create_subvol+0xd02/0x1650
+  btrfs_mksubvol+0xe95/0x12b0
+  __btrfs_ioctl_snap_create+0x2f9/0x4f0
+  btrfs_ioctl_snap_create+0x16b/0x200
+  btrfs_ioctl+0x35f0/0x5cf0
+  __x64_sys_ioctl+0x19d/0x210
+  do_syscall_64+0x3f/0xe0
+  entry_SYSCALL_64_after_hwframe+0x63/0x6b
+ ---[ end trace 0000000000000000 ]---
+
+[CAUSE]
+During create_subvol(), after inserting root item for the newly created
+subvolume, we would trigger btrfs_get_new_fs_root() to get the
+btrfs_root of that subvolume.
+
+The idea here is, we have preallocated an anonymous device number for
+the subvolume, thus we can assign it to the new subvolume.
+
+But there is really nothing preventing things like backref walk to read
+the new subvolume.
+If that happens before we call btrfs_get_new_fs_root(), the subvolume
+would be read out, with a new anonymous device number assigned already.
+
+In that case, we would trigger ASSERT(), as we really expect no one to
+read out that subvolume (which is not yet accessible from the fs).
+But things like backref walk is still possible to trigger the read on
+the subvolume.
+
+Thus our assumption on the ASSERT() is not correct in the first place.
+
+[FIX]
+Fix it by removing the ASSERT(), and just free the @anon_dev, reset it
+to 0, and continue.
+
+If the subvolume tree is read out by something else, it should have
+already get a new anon_dev assigned thus we only need to free the
+preallocated one.
+
+Reported-by: Chenyuan Yang <chenyuan0y@gmail.com>
+Fixes: 2dfb1e43f57d ("btrfs: preallocate anon block device at first phase of snapshot creation")
+CC: stable@vger.kernel.org # 5.15+
+Reviewed-by: Filipe Manana <fdmanana@suse.com>
+Signed-off-by: Qu Wenruo <wqu@suse.com>
+Reviewed-by: David Sterba <dsterba@suse.com>
+Signed-off-by: David Sterba <dsterba@suse.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ fs/btrfs/disk-io.c |   13 +++++++++++--
+ 1 file changed, 11 insertions(+), 2 deletions(-)
+
+--- a/fs/btrfs/disk-io.c
++++ b/fs/btrfs/disk-io.c
+@@ -1619,8 +1619,17 @@ static struct btrfs_root *btrfs_get_root
+ again:
+       root = btrfs_lookup_fs_root(fs_info, objectid);
+       if (root) {
+-              /* Shouldn't get preallocated anon_dev for cached roots */
+-              ASSERT(!anon_dev);
++              /*
++               * Some other caller may have read out the newly inserted
++               * subvolume already (for things like backref walk etc).  Not
++               * that common but still possible.  In that case, we just need
++               * to free the anon_dev.
++               */
++              if (unlikely(anon_dev)) {
++                      free_anon_bdev(anon_dev);
++                      anon_dev = 0;
++              }
++
+               if (check_ref && btrfs_root_refs(&root->root_item) == 0) {
+                       btrfs_put_root(root);
+                       return ERR_PTR(-ENOENT);
diff --git a/queue-5.15/btrfs-forbid-creating-subvol-qgroups.patch b/queue-5.15/btrfs-forbid-creating-subvol-qgroups.patch
new file mode 100644 (file)
index 0000000..1fa7092
--- /dev/null
@@ -0,0 +1,40 @@
+From 0c309d66dacddf8ce939b891d9ead4a8e21ad6f0 Mon Sep 17 00:00:00 2001
+From: Boris Burkov <boris@bur.io>
+Date: Wed, 10 Jan 2024 17:51:26 -0800
+Subject: btrfs: forbid creating subvol qgroups
+
+From: Boris Burkov <boris@bur.io>
+
+commit 0c309d66dacddf8ce939b891d9ead4a8e21ad6f0 upstream.
+
+Creating a qgroup 0/subvolid leads to various races and it isn't
+helpful, because you can't specify a subvol id when creating a subvol,
+so you can't be sure it will be the right one. Any requirements on the
+automatic subvol can be gratified by using a higher level qgroup and the
+inheritance parameters of subvol creation.
+
+Fixes: cecbb533b5fc ("btrfs: record simple quota deltas in delayed refs")
+CC: stable@vger.kernel.org # 4.14+
+Reviewed-by: Qu Wenruo <wqu@suse.com>
+Signed-off-by: Boris Burkov <boris@bur.io>
+Reviewed-by: David Sterba <dsterba@suse.com>
+Signed-off-by: David Sterba <dsterba@suse.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ fs/btrfs/ioctl.c |    5 +++++
+ 1 file changed, 5 insertions(+)
+
+--- a/fs/btrfs/ioctl.c
++++ b/fs/btrfs/ioctl.c
+@@ -4338,6 +4338,11 @@ static long btrfs_ioctl_qgroup_create(st
+               goto out;
+       }
++      if (sa->create && is_fstree(sa->qgroupid)) {
++              ret = -EINVAL;
++              goto out;
++      }
++
+       trans = btrfs_join_transaction(root);
+       if (IS_ERR(trans)) {
+               ret = PTR_ERR(trans);
diff --git a/queue-5.15/btrfs-forbid-deleting-live-subvol-qgroup.patch b/queue-5.15/btrfs-forbid-deleting-live-subvol-qgroup.patch
new file mode 100644 (file)
index 0000000..25bba89
--- /dev/null
@@ -0,0 +1,54 @@
+From a8df35619948bd8363d330c20a90c9a7fbff28c0 Mon Sep 17 00:00:00 2001
+From: Boris Burkov <boris@bur.io>
+Date: Wed, 10 Jan 2024 17:30:00 -0800
+Subject: btrfs: forbid deleting live subvol qgroup
+
+From: Boris Burkov <boris@bur.io>
+
+commit a8df35619948bd8363d330c20a90c9a7fbff28c0 upstream.
+
+If a subvolume still exists, forbid deleting its qgroup 0/subvolid.
+This behavior generally leads to incorrect behavior in squotas and
+doesn't have a legitimate purpose.
+
+Fixes: cecbb533b5fc ("btrfs: record simple quota deltas in delayed refs")
+CC: stable@vger.kernel.org # 5.4+
+Reviewed-by: Qu Wenruo <wqu@suse.com>
+Signed-off-by: Boris Burkov <boris@bur.io>
+Reviewed-by: David Sterba <dsterba@suse.com>
+Signed-off-by: David Sterba <dsterba@suse.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ fs/btrfs/qgroup.c |   14 ++++++++++++++
+ 1 file changed, 14 insertions(+)
+
+--- a/fs/btrfs/qgroup.c
++++ b/fs/btrfs/qgroup.c
+@@ -1608,6 +1608,15 @@ out:
+       return ret;
+ }
++static bool qgroup_has_usage(struct btrfs_qgroup *qgroup)
++{
++      return (qgroup->rfer > 0 || qgroup->rfer_cmpr > 0 ||
++              qgroup->excl > 0 || qgroup->excl_cmpr > 0 ||
++              qgroup->rsv.values[BTRFS_QGROUP_RSV_DATA] > 0 ||
++              qgroup->rsv.values[BTRFS_QGROUP_RSV_META_PREALLOC] > 0 ||
++              qgroup->rsv.values[BTRFS_QGROUP_RSV_META_PERTRANS] > 0);
++}
++
+ int btrfs_remove_qgroup(struct btrfs_trans_handle *trans, u64 qgroupid)
+ {
+       struct btrfs_fs_info *fs_info = trans->fs_info;
+@@ -1627,6 +1636,11 @@ int btrfs_remove_qgroup(struct btrfs_tra
+               goto out;
+       }
++      if (is_fstree(qgroupid) && qgroup_has_usage(qgroup)) {
++              ret = -EBUSY;
++              goto out;
++      }
++
+       /* Check if there are no children of this qgroup */
+       if (!list_empty(&qgroup->members)) {
+               ret = -EBUSY;
diff --git a/queue-5.15/btrfs-send-return-eopnotsupp-on-unknown-flags.patch b/queue-5.15/btrfs-send-return-eopnotsupp-on-unknown-flags.patch
new file mode 100644 (file)
index 0000000..f7987f9
--- /dev/null
@@ -0,0 +1,35 @@
+From f884a9f9e59206a2d41f265e7e403f080d10b493 Mon Sep 17 00:00:00 2001
+From: David Sterba <dsterba@suse.com>
+Date: Wed, 10 Jan 2024 17:48:44 +0100
+Subject: btrfs: send: return EOPNOTSUPP on unknown flags
+
+From: David Sterba <dsterba@suse.com>
+
+commit f884a9f9e59206a2d41f265e7e403f080d10b493 upstream.
+
+When some ioctl flags are checked we return EOPNOTSUPP, like for
+BTRFS_SCRUB_SUPPORTED_FLAGS, BTRFS_SUBVOL_CREATE_ARGS_MASK or fallocate
+modes. The EINVAL is supposed to be for a supported but invalid
+values or combination of options. Fix that when checking send flags so
+it's consistent with the rest.
+
+CC: stable@vger.kernel.org # 4.14+
+Link: https://lore.kernel.org/linux-btrfs/CAL3q7H5rryOLzp3EKq8RTbjMHMHeaJubfpsVLF6H4qJnKCUR1w@mail.gmail.com/
+Reviewed-by: Filipe Manana <fdmanana@suse.com>
+Signed-off-by: David Sterba <dsterba@suse.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ fs/btrfs/send.c |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+--- a/fs/btrfs/send.c
++++ b/fs/btrfs/send.c
+@@ -7558,7 +7558,7 @@ long btrfs_ioctl_send(struct file *mnt_f
+       }
+       if (arg->flags & ~BTRFS_SEND_FLAG_MASK) {
+-              ret = -EINVAL;
++              ret = -EOPNOTSUPP;
+               goto out;
+       }
index afd99c15699e0c2268fbb0f35dd45115ed405906..acb65d93c4ac5ac2bed27291ab31ff3baeb1c616 100644 (file)
@@ -350,3 +350,7 @@ clocksource-skip-watchdog-check-for-large-watchdog-intervals.patch
 net-stmmac-xgmac-use-define-for-string-constants.patch
 net-stmmac-xgmac-fix-a-typo-of-register-name-in-dpp-safety-handling.patch
 netfilter-nft_set_rbtree-skip-end-interval-element-from-gc.patch
+btrfs-forbid-creating-subvol-qgroups.patch
+btrfs-do-not-assert-if-the-newly-created-subvolume-already-got-read.patch
+btrfs-forbid-deleting-live-subvol-qgroup.patch
+btrfs-send-return-eopnotsupp-on-unknown-flags.patch