summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKent Overstreet <kent.overstreet@gmail.com>2021-11-23 19:00:23 -0500
committerKent Overstreet <kent.overstreet@gmail.com>2021-12-30 17:56:33 -0500
commit1c8b45062446dc6e4a6501c20a0c7a87f31d3eaf (patch)
treec1ad369c605286a218457940376d5e49df12d47f
parent7afda3e6cb82237561c7f503f76f8104dfc8160c (diff)
bcachefs: Apply workaround for too many btree iters to read path
Reading from cached data, which calls bch2_bucket_io_time_reset(), is leading to transaction iterator overflows - this standardizes the workaround. Signed-off-by: Kent Overstreet <kent.overstreet@gmail.com>
-rw-r--r--fs/bcachefs/btree_iter.h8
-rw-r--r--fs/bcachefs/dirent.c5
-rw-r--r--fs/bcachefs/fs-io.c4
-rw-r--r--fs/bcachefs/io.c4
4 files changed, 17 insertions, 4 deletions
diff --git a/fs/bcachefs/btree_iter.h b/fs/bcachefs/btree_iter.h
index 33a703c27f7a..31d2dda7ca05 100644
--- a/fs/bcachefs/btree_iter.h
+++ b/fs/bcachefs/btree_iter.h
@@ -302,13 +302,19 @@ static inline struct bkey_s_c __bch2_btree_iter_peek(struct btree_iter *iter,
: bch2_btree_iter_peek(iter);
}
+static inline int btree_trans_too_many_iters(struct btree_trans *trans)
+{
+ return hweight64(trans->paths_allocated) > BTREE_ITER_MAX / 2
+ ? -EINTR : 0;
+}
+
static inline struct bkey_s_c
__bch2_btree_iter_peek_and_restart(struct btree_trans *trans,
struct btree_iter *iter, unsigned flags)
{
struct bkey_s_c k;
- while ((hweight64(trans->paths_allocated) > BTREE_ITER_MAX / 2) ||
+ while (btree_trans_too_many_iters(trans) ||
(k = __bch2_btree_iter_peek(iter, flags),
bkey_err(k) == -EINTR))
bch2_trans_begin(trans);
diff --git a/fs/bcachefs/dirent.c b/fs/bcachefs/dirent.c
index 4dfcc955675b..fe4a85a6a8cb 100644
--- a/fs/bcachefs/dirent.c
+++ b/fs/bcachefs/dirent.c
@@ -531,10 +531,9 @@ retry:
* read_target looks up subvolumes, we can overflow paths if the
* directory has many subvolumes in it
*/
- if (hweight64(trans.paths_allocated) > BTREE_ITER_MAX / 2) {
- ret = -EINTR;
+ ret = btree_trans_too_many_iters(&trans);
+ if (ret)
break;
- }
}
bch2_trans_iter_exit(&trans, &iter);
err:
diff --git a/fs/bcachefs/fs-io.c b/fs/bcachefs/fs-io.c
index 19946375ea5c..1e4c122bfee7 100644
--- a/fs/bcachefs/fs-io.c
+++ b/fs/bcachefs/fs-io.c
@@ -898,6 +898,10 @@ retry:
swap(rbio->bio.bi_iter.bi_size, bytes);
bio_advance(&rbio->bio, bytes);
+
+ ret = btree_trans_too_many_iters(trans);
+ if (ret)
+ break;
}
err:
bch2_trans_iter_exit(trans, &iter);
diff --git a/fs/bcachefs/io.c b/fs/bcachefs/io.c
index 3a6b4446706d..5a3c9eff1b50 100644
--- a/fs/bcachefs/io.c
+++ b/fs/bcachefs/io.c
@@ -2323,6 +2323,10 @@ retry:
swap(bvec_iter.bi_size, bytes);
bio_advance_iter(&rbio->bio, &bvec_iter, bytes);
+
+ ret = btree_trans_too_many_iters(&trans);
+ if (ret)
+ break;
}
err:
bch2_trans_iter_exit(&trans, &iter);