139 lines
4.7 KiB
Diff
139 lines
4.7 KiB
Diff
From 0e796cf8047d1e35c77573a8ef62f13e6d242b76 Mon Sep 17 00:00:00 2001
|
|
From: Kent Overstreet <kent.overstreet@linux.dev>
|
|
Date: Tue, 23 Apr 2024 02:18:18 -0400
|
|
Subject: [PATCH 114/233] bcachefs: btree_write_buffer_flush_seq() no longer
|
|
closes journal
|
|
Content-Type: text/plain; charset="utf-8"
|
|
Content-Transfer-Encoding: 8bit
|
|
|
|
Signed-off-by: Kent Overstreet <kent.overstreet@linux.dev>
|
|
Signed-off-by: Alexander Miroshnichenko <alex@millerson.name>
|
|
---
|
|
fs/bcachefs/btree_write_buffer.c | 19 ++++++++++++++-----
|
|
fs/bcachefs/journal.c | 27 ++++++++++++++++++++-------
|
|
fs/bcachefs/journal.h | 2 +-
|
|
3 files changed, 35 insertions(+), 13 deletions(-)
|
|
|
|
diff --git a/fs/bcachefs/btree_write_buffer.c b/fs/bcachefs/btree_write_buffer.c
|
|
index 1bd26221f156..49ce2d1e5c02 100644
|
|
--- a/fs/bcachefs/btree_write_buffer.c
|
|
+++ b/fs/bcachefs/btree_write_buffer.c
|
|
@@ -495,10 +495,6 @@ static int bch2_journal_keys_to_write_buffer(struct bch_fs *c, struct journal_bu
|
|
|
|
entry->type = BCH_JSET_ENTRY_btree_keys;
|
|
}
|
|
-
|
|
- spin_lock(&c->journal.lock);
|
|
- buf->need_flush_to_write_buffer = false;
|
|
- spin_unlock(&c->journal.lock);
|
|
out:
|
|
ret = bch2_journal_keys_to_write_buffer_end(c, &dst) ?: ret;
|
|
return ret;
|
|
@@ -508,11 +504,24 @@ static int fetch_wb_keys_from_journal(struct bch_fs *c, u64 max_seq)
|
|
{
|
|
struct journal *j = &c->journal;
|
|
struct journal_buf *buf;
|
|
+ bool blocked;
|
|
int ret = 0;
|
|
|
|
- while (!ret && (buf = bch2_next_write_buffer_flush_journal_buf(j, max_seq))) {
|
|
+ while (!ret && (buf = bch2_next_write_buffer_flush_journal_buf(j, max_seq, &blocked))) {
|
|
ret = bch2_journal_keys_to_write_buffer(c, buf);
|
|
+
|
|
+ if (!blocked && !ret) {
|
|
+ spin_lock(&j->lock);
|
|
+ buf->need_flush_to_write_buffer = false;
|
|
+ spin_unlock(&j->lock);
|
|
+ }
|
|
+
|
|
mutex_unlock(&j->buf_lock);
|
|
+
|
|
+ if (blocked) {
|
|
+ bch2_journal_unblock(j);
|
|
+ break;
|
|
+ }
|
|
}
|
|
|
|
return ret;
|
|
diff --git a/fs/bcachefs/journal.c b/fs/bcachefs/journal.c
|
|
index bfbb1ac60c3d..699db0d0749a 100644
|
|
--- a/fs/bcachefs/journal.c
|
|
+++ b/fs/bcachefs/journal.c
|
|
@@ -908,6 +908,8 @@ static void __bch2_journal_block(struct journal *j)
|
|
new.v = old.v;
|
|
new.cur_entry_offset = JOURNAL_ENTRY_BLOCKED_VAL;
|
|
} while (!atomic64_try_cmpxchg(&j->reservations.counter, &old.v, new.v));
|
|
+
|
|
+ journal_cur_buf(j)->data->u64s = cpu_to_le32(old.cur_entry_offset);
|
|
}
|
|
}
|
|
|
|
@@ -920,7 +922,8 @@ void bch2_journal_block(struct journal *j)
|
|
journal_quiesce(j);
|
|
}
|
|
|
|
-static struct journal_buf *__bch2_next_write_buffer_flush_journal_buf(struct journal *j, u64 max_seq)
|
|
+static struct journal_buf *__bch2_next_write_buffer_flush_journal_buf(struct journal *j,
|
|
+ u64 max_seq, bool *blocked)
|
|
{
|
|
struct journal_buf *ret = NULL;
|
|
|
|
@@ -937,13 +940,17 @@ static struct journal_buf *__bch2_next_write_buffer_flush_journal_buf(struct jou
|
|
struct journal_buf *buf = j->buf + idx;
|
|
|
|
if (buf->need_flush_to_write_buffer) {
|
|
- if (seq == journal_cur_seq(j))
|
|
- __journal_entry_close(j, JOURNAL_ENTRY_CLOSED_VAL, true);
|
|
-
|
|
union journal_res_state s;
|
|
s.v = atomic64_read_acquire(&j->reservations.counter);
|
|
|
|
- ret = journal_state_count(s, idx)
|
|
+ unsigned open = seq == journal_cur_seq(j) && __journal_entry_is_open(s);
|
|
+
|
|
+ if (open && !*blocked) {
|
|
+ __bch2_journal_block(j);
|
|
+ *blocked = true;
|
|
+ }
|
|
+
|
|
+ ret = journal_state_count(s, idx) > open
|
|
? ERR_PTR(-EAGAIN)
|
|
: buf;
|
|
break;
|
|
@@ -956,11 +963,17 @@ static struct journal_buf *__bch2_next_write_buffer_flush_journal_buf(struct jou
|
|
return ret;
|
|
}
|
|
|
|
-struct journal_buf *bch2_next_write_buffer_flush_journal_buf(struct journal *j, u64 max_seq)
|
|
+struct journal_buf *bch2_next_write_buffer_flush_journal_buf(struct journal *j,
|
|
+ u64 max_seq, bool *blocked)
|
|
{
|
|
struct journal_buf *ret;
|
|
+ *blocked = false;
|
|
+
|
|
+ wait_event(j->wait, (ret = __bch2_next_write_buffer_flush_journal_buf(j,
|
|
+ max_seq, blocked)) != ERR_PTR(-EAGAIN));
|
|
+ if (IS_ERR_OR_NULL(ret) && *blocked)
|
|
+ bch2_journal_unblock(j);
|
|
|
|
- wait_event(j->wait, (ret = __bch2_next_write_buffer_flush_journal_buf(j, max_seq)) != ERR_PTR(-EAGAIN));
|
|
return ret;
|
|
}
|
|
|
|
diff --git a/fs/bcachefs/journal.h b/fs/bcachefs/journal.h
|
|
index 6d3c839bbbef..71a50846967f 100644
|
|
--- a/fs/bcachefs/journal.h
|
|
+++ b/fs/bcachefs/journal.h
|
|
@@ -425,7 +425,7 @@ static inline void bch2_journal_set_replay_done(struct journal *j)
|
|
|
|
void bch2_journal_unblock(struct journal *);
|
|
void bch2_journal_block(struct journal *);
|
|
-struct journal_buf *bch2_next_write_buffer_flush_journal_buf(struct journal *j, u64 max_seq);
|
|
+struct journal_buf *bch2_next_write_buffer_flush_journal_buf(struct journal *, u64, bool *);
|
|
|
|
void __bch2_journal_debug_to_text(struct printbuf *, struct journal *);
|
|
void bch2_journal_debug_to_text(struct printbuf *, struct journal *);
|
|
--
|
|
2.45.2
|
|
|