From: Filipe Manana <fdmanana@kernel.org>
To: David Sterba <dsterba@suse.com>
Cc: linux-btrfs@vger.kernel.org
Subject: Re: [PATCH 7/8] btrfs: relocation: use on-stack iterator in build_backref_tree
Date: Wed, 4 Oct 2023 13:35:26 +0100 [thread overview]
Message-ID: <CAL3q7H6wryrNsjk8HZqqiSyMHTcxcPC-kd2U-uCEVxWYHAPV2Q@mail.gmail.com> (raw)
In-Reply-To: <7588cec46a2d548400de33930811fa12026f1dd1.1695380646.git.dsterba@suse.com>
On Fri, Sep 22, 2023 at 2:26 PM David Sterba <dsterba@suse.com> wrote:
>
> build_backref_tree() is called in a loop by relocate_tree_blocks()
> for each relocated block. The iterator is allocated and freed repeatedly
> while we could simply use an on-stack variable to avoid the allocation
> and remove one more failure case. The stack grows by 48 bytes.
>
> This was the only use of btrfs_backref_iter_alloc() so it's changed to
> be an initializer and btrfs_backref_iter_free() can be removed
> completely.
>
> Signed-off-by: David Sterba <dsterba@suse.com>
> ---
> fs/btrfs/backref.c | 26 ++++++++++----------------
> fs/btrfs/backref.h | 11 ++---------
> fs/btrfs/relocation.c | 12 ++++++------
> 3 files changed, 18 insertions(+), 31 deletions(-)
>
> diff --git a/fs/btrfs/backref.c b/fs/btrfs/backref.c
> index 0dc91bf654b5..691b20b47065 100644
> --- a/fs/btrfs/backref.c
> +++ b/fs/btrfs/backref.c
> @@ -2828,26 +2828,20 @@ void free_ipath(struct inode_fs_paths *ipath)
> kfree(ipath);
> }
>
> -struct btrfs_backref_iter *btrfs_backref_iter_alloc(struct btrfs_fs_info *fs_info)
> +int btrfs_backref_iter_init(struct btrfs_fs_info *fs_info,
> + struct btrfs_backref_iter *iter)
> {
> - struct btrfs_backref_iter *ret;
> -
> - ret = kzalloc(sizeof(*ret), GFP_NOFS);
> - if (!ret)
> - return NULL;
> -
> - ret->path = btrfs_alloc_path();
> - if (!ret->path) {
> - kfree(ret);
> - return NULL;
> - }
> + memset(iter, 0, sizeof(struct btrfs_backref_iter));
> + iter->path = btrfs_alloc_path();
So this is breaking misc-next, as paths are leaking here, easily
visible after "rmmod btrfs":
[ 2265.115295] =============================================================================
[ 2265.115938] BUG btrfs_path (Not tainted): Objects remaining in
btrfs_path on __kmem_cache_shutdown()
[ 2265.116615] -----------------------------------------------------------------------------
[ 2265.117614] Slab 0x00000000dbb6fd30 objects=36 used=3
fp=0x000000001768ab21
flags=0x17fffc000000800(slab|node=0|zone=2|lastcpupid=0x1ffff)
[ 2265.118423] CPU: 1 PID: 402761 Comm: rmmod Not tainted
6.6.0-rc3-btrfs-next-139+ #1
[ 2265.118440] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996),
BIOS rel-1.16.2-0-gea1b7a073390-prebuilt.qemu.org 04/01/2014
[ 2265.118457] Call Trace:
[ 2265.118483] <TASK>
[ 2265.118491] dump_stack_lvl+0x44/0x60
[ 2265.118521] slab_err+0xb6/0xf0
[ 2265.118547] __kmem_cache_shutdown+0x15f/0x2f0
[ 2265.118565] kmem_cache_destroy+0x4c/0x170
[ 2265.118588] exit_btrfs_fs+0x24/0x40 [btrfs]
[ 2265.119121] __x64_sys_delete_module+0x193/0x290
[ 2265.119137] ? exit_to_user_mode_prepare+0x3d/0x170
[ 2265.119154] do_syscall_64+0x38/0x90
[ 2265.119169] entry_SYSCALL_64_after_hwframe+0x6e/0xd8
[ 2265.119185] RIP: 0033:0x7f55ec127997
[ 2265.119199] Code: 73 01 c3 48 8b 0d 81 94 0c 00 f7 d8 64 89 01 48
83 c8 ff c3 66 2e 0f 1f 84 00 00 00 00 00 0f 1f 44 00 00 b8 b0 00 00
00 0f 05 <48> 3d 01 f0 ff ff 73 01 c3 48 8b 0d 51 94 0c 00 f7 d8 64 89
01 48
[ 2265.119210] RSP: 002b:00007ffe06412d98 EFLAGS: 00000206 ORIG_RAX:
00000000000000b0
[ 2265.119225] RAX: ffffffffffffffda RBX: 00005589627f26f0 RCX: 00007f55ec127997
[ 2265.119234] RDX: 0000000000000000 RSI: 0000000000000800 RDI: 00005589627f2758
[ 2265.119241] RBP: 0000000000000000 R08: 1999999999999999 R09: 0000000000000000
[ 2265.119249] R10: 00007f55ec19aac0 R11: 0000000000000206 R12: 00007ffe06412fe0
[ 2265.119257] R13: 00007ffe064133da R14: 00005589627f22a0 R15: 00007ffe06412fe8
[ 2265.119276] </TASK>
[ 2265.119281] Disabling lock debugging due to kernel taint
[ 2265.119289] Object 0x0000000062d6ea78 @offset=784
[ 2265.120073] Object 0x0000000042bd66e6 @offset=1904
[ 2265.120712] Object 0x00000000603962f0 @offset=2240
[ 2265.121397] =============================================================================
[ 2265.122021] BUG btrfs_path (Tainted: G B ): Objects
remaining in btrfs_path on __kmem_cache_shutdown()
(...)
I get thousands and thousands of these messages after running fstests
and doing "rmmod btrfs".
The problem here is the code is reusing the iterator, and every time
allocating a new path without freeing the previous one.
It could simply avoid path allocation and reuse it.
Thanks.
> + if (!iter->path)
> + return -ENOMEM;
>
> /* Current backref iterator only supports iteration in commit root */
> - ret->path->search_commit_root = 1;
> - ret->path->skip_locking = 1;
> - ret->fs_info = fs_info;
> + iter->path->search_commit_root = 1;
> + iter->path->skip_locking = 1;
> + iter->fs_info = fs_info;
>
> - return ret;
> + return 0;
> }
>
> int btrfs_backref_iter_start(struct btrfs_backref_iter *iter, u64 bytenr)
> diff --git a/fs/btrfs/backref.h b/fs/btrfs/backref.h
> index 83a9a34e948e..24fabbd2a80a 100644
> --- a/fs/btrfs/backref.h
> +++ b/fs/btrfs/backref.h
> @@ -269,15 +269,8 @@ struct btrfs_backref_iter {
> u32 end_ptr;
> };
>
> -struct btrfs_backref_iter *btrfs_backref_iter_alloc(struct btrfs_fs_info *fs_info);
> -
> -static inline void btrfs_backref_iter_free(struct btrfs_backref_iter *iter)
> -{
> - if (!iter)
> - return;
> - btrfs_free_path(iter->path);
> - kfree(iter);
> -}
> +int btrfs_backref_iter_init(struct btrfs_fs_info *fs_info,
> + struct btrfs_backref_iter *iter);
>
> static inline struct extent_buffer *btrfs_backref_get_eb(
> struct btrfs_backref_iter *iter)
> diff --git a/fs/btrfs/relocation.c b/fs/btrfs/relocation.c
> index d1dcbb15baa7..6a31e73c3df7 100644
> --- a/fs/btrfs/relocation.c
> +++ b/fs/btrfs/relocation.c
> @@ -464,7 +464,7 @@ static noinline_for_stack struct btrfs_backref_node *build_backref_tree(
> struct reloc_control *rc, struct btrfs_key *node_key,
> int level, u64 bytenr)
> {
> - struct btrfs_backref_iter *iter;
> + struct btrfs_backref_iter iter;
> struct btrfs_backref_cache *cache = &rc->backref_cache;
> /* For searching parent of TREE_BLOCK_REF */
> struct btrfs_path *path;
> @@ -474,9 +474,9 @@ static noinline_for_stack struct btrfs_backref_node *build_backref_tree(
> int ret;
> int err = 0;
>
> - iter = btrfs_backref_iter_alloc(rc->extent_root->fs_info);
> - if (!iter)
> - return ERR_PTR(-ENOMEM);
> + ret = btrfs_backref_iter_init(rc->extent_root->fs_info, &iter);
> + if (ret < 0)
> + return ERR_PTR(ret);
> path = btrfs_alloc_path();
> if (!path) {
> err = -ENOMEM;
> @@ -494,7 +494,7 @@ static noinline_for_stack struct btrfs_backref_node *build_backref_tree(
>
> /* Breadth-first search to build backref cache */
> do {
> - ret = btrfs_backref_add_tree_node(cache, path, iter, node_key,
> + ret = btrfs_backref_add_tree_node(cache, path, &iter, node_key,
> cur);
> if (ret < 0) {
> err = ret;
> @@ -522,7 +522,7 @@ static noinline_for_stack struct btrfs_backref_node *build_backref_tree(
> if (handle_useless_nodes(rc, node))
> node = NULL;
> out:
> - btrfs_backref_iter_free(iter);
> + btrfs_backref_iter_release(&iter);
> btrfs_free_path(path);
> if (err) {
> btrfs_backref_error_cleanup(cache, node);
> --
> 2.41.0
>
next prev parent reply other threads:[~2023-10-04 12:37 UTC|newest]
Thread overview: 29+ messages / expand[flat|nested] mbox.gz Atom feed top
2023-09-22 11:07 [PATCH 0/8] Minor cleanups in relocation.c David Sterba
2023-09-22 11:07 ` [PATCH 1/8] btrfs: relocation: use more natural types for tree_block bitfields David Sterba
2023-09-22 12:28 ` Johannes Thumshirn
2023-09-22 22:28 ` Qu Wenruo
2023-09-22 11:07 ` [PATCH 2/8] btrfs: relocation: use enum for stages David Sterba
2023-09-22 12:29 ` Johannes Thumshirn
2023-09-22 22:29 ` Qu Wenruo
2023-09-25 13:44 ` David Sterba
2023-09-22 11:07 ` [PATCH 3/8] btrfs: relocation: switch bitfields to bool in reloc_control David Sterba
2023-09-22 12:30 ` Johannes Thumshirn
2023-09-22 22:30 ` Qu Wenruo
2023-09-22 11:07 ` [PATCH 4/8] btrfs: relocation: open code mapping_tree_init David Sterba
2023-09-22 12:31 ` Johannes Thumshirn
2023-09-22 22:31 ` Qu Wenruo
2023-09-22 11:07 ` [PATCH 5/8] btrfs: switch btrfs_backref_cache::is_reloc to bool David Sterba
2023-09-22 12:31 ` Johannes Thumshirn
2023-09-22 22:31 ` Qu Wenruo
2023-09-22 11:07 ` [PATCH 6/8] btrfs: relocation: return bool from btrfs_should_ignore_reloc_root David Sterba
2023-09-22 12:36 ` Johannes Thumshirn
2023-09-22 18:35 ` David Sterba
2023-09-22 22:32 ` Qu Wenruo
2023-09-22 11:07 ` [PATCH 7/8] btrfs: relocation: use on-stack iterator in build_backref_tree David Sterba
2023-09-22 12:46 ` Johannes Thumshirn
2023-09-22 22:35 ` Qu Wenruo
2023-09-25 13:42 ` David Sterba
2023-10-04 12:35 ` Filipe Manana [this message]
2023-10-04 12:46 ` David Sterba
2023-09-22 11:07 ` [PATCH 8/8] btrfs: relocation: constify parameters where possible David Sterba
2023-09-22 12:43 ` Johannes Thumshirn
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=CAL3q7H6wryrNsjk8HZqqiSyMHTcxcPC-kd2U-uCEVxWYHAPV2Q@mail.gmail.com \
--to=fdmanana@kernel.org \
--cc=dsterba@suse.com \
--cc=linux-btrfs@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).