On Wed, Apr 03, 2019 at 10:38:09PM -0400, Jeff Mahoney wrote: > On 4/2/19 3:19 PM, Filipe Manana wrote: > > On Tue, Apr 2, 2019 at 7:29 PM <jeffm@xxxxxxxx> wrote: > >> > >> From: Jeff Mahoney <jeffm@xxxxxxxx> > >> > >> When repairing the extent tree, it's possible for delayed extents to > >> be created when running btrfs_write_dirty_block_groups. We run > >> delayed refs one last time in the kernel but that is missing in > >> the userspace tools. > >> > >> That results in delayed refs getting dropped on the floor, the extent > >> records not getting created, and in the next tranaction, when the > >> extent tree is CoW'd again, we hit the BUG_ON when we can't find > >> the extent record. > >> > >> We can fix this by running the delayed refs after writing out the > >> dirty block groups. > >> > >> Signed-off-by: Jeff Mahoney <jeffm@xxxxxxxx> > >> --- > >> transaction.c | 2 ++ > >> 1 file changed, 2 insertions(+) > >> > >> diff --git a/transaction.c b/transaction.c > >> index e756db33..2f19e9c8 100644 > >> --- a/transaction.c > >> +++ b/transaction.c > >> @@ -194,6 +194,8 @@ commit_tree: > >> ret = btrfs_run_delayed_refs(trans, -1); > >> BUG_ON(ret); > >> btrfs_write_dirty_block_groups(trans); > >> + ret = btrfs_run_delayed_refs(trans, -1); > >> + BUG_ON(ret); > > > > And running delayed refs can dirty more block groups as well. > > At this point shouldn't we loop running delayed refs until no more > > dirty block groups exist? Just like in the kernel. > > Right. This is another argument for code sharing between the kernel and > userspace. Sharing code in this function would be really hard, I've implemented the loop in commit in progs.
