bcachefs: bch2_foreground_maybe_merge() now correctly reports lock restarts
authorKent Overstreet <kent.overstreet@gmail.com>
Wed, 31 Mar 2021 20:16:39 +0000 (16:16 -0400)
committerKent Overstreet <kent.overstreet@linux.dev>
Sun, 22 Oct 2023 21:08:58 +0000 (17:08 -0400)
This means that btree node splits don't have to automatically trigger a
transaction restart.

Signed-off-by: Kent Overstreet <kent.overstreet@gmail.com>
Signed-off-by: Kent Overstreet <kent.overstreet@linux.dev>
fs/bcachefs/btree_update_interior.c
fs/bcachefs/btree_update_interior.h

index af7c2df56692c2648af15a664773b4d52721e986..988922699e8bb808720c82e5704d336be417c190 100644 (file)
@@ -1527,16 +1527,16 @@ int bch2_btree_split_leaf(struct bch_fs *c, struct btree_iter *iter,
        bch2_btree_update_done(as);
 
        for (l = iter->level + 1; btree_iter_node(iter, l) && !ret; l++)
-               bch2_foreground_maybe_merge(c, iter, l, flags);
+               ret = bch2_foreground_maybe_merge(c, iter, l, flags);
 
        return ret;
 }
 
-void __bch2_foreground_maybe_merge(struct bch_fs *c,
-                                  struct btree_iter *iter,
-                                  unsigned level,
-                                  unsigned flags,
-                                  enum btree_node_sibling sib)
+int __bch2_foreground_maybe_merge(struct bch_fs *c,
+                                 struct btree_iter *iter,
+                                 unsigned level,
+                                 unsigned flags,
+                                 enum btree_node_sibling sib)
 {
        struct btree_trans *trans = iter->trans;
        struct btree_iter *sib_iter = NULL;
@@ -1547,10 +1547,7 @@ void __bch2_foreground_maybe_merge(struct bch_fs *c,
        struct btree *b, *m, *n, *prev, *next, *parent;
        struct bpos sib_pos;
        size_t sib_u64s;
-       int ret = 0;
-
-       if (trans->nounlock)
-               return;
+       int ret = 0, ret2 = 0;
 
        BUG_ON(!btree_node_locked(iter, level));
 retry:
@@ -1689,17 +1686,16 @@ out:
         * split path, and downgrading to read locks in there is potentially
         * confusing:
         */
-       return;
+       return ret ?: ret2;
 err:
        bch2_trans_iter_put(trans, sib_iter);
        sib_iter = NULL;
 
-       if (ret == -EINTR && bch2_trans_relock(trans)) {
-               ret = 0;
+       if (ret == -EINTR && bch2_trans_relock(trans))
                goto retry;
-       }
 
        if (ret == -EINTR && !(flags & BTREE_INSERT_NOUNLOCK)) {
+               ret2 = ret;
                ret = bch2_btree_iter_traverse_all(trans);
                if (!ret)
                        goto retry;
index 2a6b51ece0f8e30eeff4e1473a5a53da29922243..f2925b0d7f17eacfd7773cc4a7e57b3180cc4024 100644 (file)
@@ -132,10 +132,10 @@ void bch2_btree_insert_node(struct btree_update *, struct btree *,
                            unsigned);
 int bch2_btree_split_leaf(struct bch_fs *, struct btree_iter *, unsigned);
 
-void __bch2_foreground_maybe_merge(struct bch_fs *, struct btree_iter *,
-                                  unsigned, unsigned, enum btree_node_sibling);
+int __bch2_foreground_maybe_merge(struct bch_fs *, struct btree_iter *,
+                                 unsigned, unsigned, enum btree_node_sibling);
 
-static inline void bch2_foreground_maybe_merge_sibling(struct bch_fs *c,
+static inline int bch2_foreground_maybe_merge_sibling(struct bch_fs *c,
                                        struct btree_iter *iter,
                                        unsigned level, unsigned flags,
                                        enum btree_node_sibling sib)
@@ -143,27 +143,27 @@ static inline void bch2_foreground_maybe_merge_sibling(struct bch_fs *c,
        struct btree *b;
 
        if (iter->uptodate >= BTREE_ITER_NEED_TRAVERSE)
-               return;
+               return 0;
 
        if (!bch2_btree_node_relock(iter, level))
-               return;
+               return 0;
 
        b = iter->l[level].b;
        if (b->sib_u64s[sib] > c->btree_foreground_merge_threshold)
-               return;
+               return 0;
 
-       __bch2_foreground_maybe_merge(c, iter, level, flags, sib);
+       return __bch2_foreground_maybe_merge(c, iter, level, flags, sib);
 }
 
-static inline void bch2_foreground_maybe_merge(struct bch_fs *c,
+static inline int bch2_foreground_maybe_merge(struct bch_fs *c,
                                               struct btree_iter *iter,
                                               unsigned level,
                                               unsigned flags)
 {
-       bch2_foreground_maybe_merge_sibling(c, iter, level, flags,
-                                           btree_prev_sib);
-       bch2_foreground_maybe_merge_sibling(c, iter, level, flags,
-                                           btree_next_sib);
+       return  bch2_foreground_maybe_merge_sibling(c, iter, level, flags,
+                                                   btree_prev_sib) ?:
+               bch2_foreground_maybe_merge_sibling(c, iter, level, flags,
+                                                   btree_next_sib);
 }
 
 void bch2_btree_set_root_for_read(struct bch_fs *, struct btree *);