Skip to content

Commit c6c9991

Browse files
loemrawkdave
authored andcommitted
btrfs: fix delayed_node ref_tracker use after free
Move the print before releasing the delayed node. In my initial testing there was a bug that was causing delayed_nodes to not get freed which is why I put the print after the release. This obviously neglects the case where the delayed node is properly freed. Add condition to make sure we only print if we have more than one reference to the delayed_node to prevent printing when we only have the reference taken in btrfs_kill_all_delayed_nodes(). Fixes: b767a28 ("btrfs: print leaked references in kill_all_delayed_nodes()") Tested-by: Christoph Hellwig <hch@lst.de> Signed-off-by: Leo Martins <loemra.dev@gmail.com> Reviewed-by: David Sterba <dsterba@suse.com> Signed-off-by: David Sterba <dsterba@suse.com>
1 parent ef08382 commit c6c9991

File tree

2 files changed

+8
-1
lines changed

2 files changed

+8
-1
lines changed

fs/btrfs/delayed-inode.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2110,9 +2110,9 @@ void btrfs_kill_all_delayed_nodes(struct btrfs_root *root)
21102110

21112111
for (int i = 0; i < count; i++) {
21122112
__btrfs_kill_delayed_node(delayed_nodes[i]);
2113+
btrfs_delayed_node_ref_tracker_dir_print(delayed_nodes[i]);
21132114
btrfs_release_delayed_node(delayed_nodes[i],
21142115
&delayed_node_trackers[i]);
2115-
btrfs_delayed_node_ref_tracker_dir_print(delayed_nodes[i]);
21162116
}
21172117
}
21182118
}

fs/btrfs/delayed-inode.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -219,6 +219,13 @@ static inline void btrfs_delayed_node_ref_tracker_dir_print(struct btrfs_delayed
219219
if (!btrfs_test_opt(node->root->fs_info, REF_TRACKER))
220220
return;
221221

222+
/*
223+
* Only print if there are leaked references. The caller is
224+
* holding one reference, so if refs == 1 there is no leak.
225+
*/
226+
if (refcount_read(&node->refs) == 1)
227+
return;
228+
222229
ref_tracker_dir_print(&node->ref_dir.dir,
223230
BTRFS_DELAYED_NODE_REF_TRACKER_DISPLAY_LIMIT);
224231
}

0 commit comments

Comments
 (0)