Messages in this thread Patch in this message | | | From | Kent Overstreet <> | Subject | [PATCH 16/21] bcachefs: bch2_verify_accounting_clean() | Date | Sat, 24 Feb 2024 21:38:18 -0500 |
| |
Verify that the in-memory accounting verifies the on-disk accounting after a clean shutdown.
Signed-off-by: Kent Overstreet <kent.overstreet@linux.dev> --- fs/bcachefs/disk_accounting.c | 27 +++++++++++++++++++++++++++ fs/bcachefs/disk_accounting.h | 4 +++- fs/bcachefs/super.c | 1 + 3 files changed, 31 insertions(+), 1 deletion(-)
diff --git a/fs/bcachefs/disk_accounting.c b/fs/bcachefs/disk_accounting.c index 2884615adc1e..8d7b6ab66e71 100644 --- a/fs/bcachefs/disk_accounting.c +++ b/fs/bcachefs/disk_accounting.c @@ -513,6 +513,33 @@ int bch2_dev_usage_init(struct bch_dev *ca, bool gc) return ret; } +void bch2_verify_accounting_clean(struct bch_fs *c) +{ + bch2_trans_run(c, + for_each_btree_key(trans, iter, + BTREE_ID_accounting, POS_MIN, + BTREE_ITER_ALL_SNAPSHOTS, k, ({ + u64 v[BCH_ACCOUNTING_MAX_COUNTERS]; + struct bkey_s_c_accounting a = bkey_s_c_to_accounting(k); + unsigned nr = bch2_accounting_counters(k.k); + + bch2_accounting_mem_read(c, k.k->p, v, nr); + + if (memcmp(a.v->d, v, nr * sizeof(u64))) { + struct printbuf buf = PRINTBUF; + + bch2_bkey_val_to_text(&buf, c, k); + prt_str(&buf, " in mem"); + for (unsigned j = 0; j < nr; j++) + prt_printf(&buf, " %llu", v[j]); + + WARN(1, "accounting mismatch: %s", buf.buf); + printbuf_exit(&buf); + } + 0; + }))); +} + void bch2_accounting_free(struct bch_accounting_mem *acc) { darray_exit(&acc->k); diff --git a/fs/bcachefs/disk_accounting.h b/fs/bcachefs/disk_accounting.h index 70ac67f4a3cb..a0cf7a0b84a7 100644 --- a/fs/bcachefs/disk_accounting.h +++ b/fs/bcachefs/disk_accounting.h @@ -164,7 +164,7 @@ static inline void bch2_accounting_mem_read_counters(struct bch_fs *c, unsigned { memset(v, 0, sizeof(*v) * nr); - struct bch_accounting_mem *acc = &c->accounting[0]; + struct bch_accounting_mem *acc = &c->accounting[gc]; if (unlikely(idx >= acc->k.nr)) return; @@ -194,6 +194,8 @@ int bch2_accounting_read(struct bch_fs *); int bch2_dev_usage_remove(struct bch_fs *, unsigned); int bch2_dev_usage_init(struct bch_dev *, bool); +void bch2_verify_accounting_clean(struct bch_fs *c); + void bch2_accounting_free(struct bch_accounting_mem *); void bch2_fs_accounting_exit(struct bch_fs *); diff --git a/fs/bcachefs/super.c b/fs/bcachefs/super.c index 6617c8912e51..201d7767e478 100644 --- a/fs/bcachefs/super.c +++ b/fs/bcachefs/super.c @@ -355,6 +355,7 @@ void bch2_fs_read_only(struct bch_fs *c) BUG_ON(atomic_long_read(&c->btree_key_cache.nr_dirty)); BUG_ON(c->btree_write_buffer.inc.keys.nr); BUG_ON(c->btree_write_buffer.flushing.keys.nr); + bch2_verify_accounting_clean(c); bch_verbose(c, "marking filesystem clean"); bch2_fs_mark_clean(c); -- 2.43.0
| |