bcachefs: Add a mempool for btree_trans bump allocator
This allocation is required for filesystem operations to make forward progress, thus needs a mempool. Signed-off-by: Kent Overstreet <kent.overstreet@gmail.com> Signed-off-by: Kent Overstreet <kent.overstreet@linux.dev>
This commit is contained in:
parent
9ae28f824e
commit
e131b6aa0a
@ -644,6 +644,7 @@ struct bch_fs {
|
||||
struct mutex btree_trans_lock;
|
||||
struct list_head btree_trans_list;
|
||||
mempool_t btree_iters_pool;
|
||||
mempool_t btree_trans_mem_pool;
|
||||
struct btree_iter_buf __percpu *btree_iters_bufs;
|
||||
|
||||
struct srcu_struct btree_trans_barrier;
|
||||
|
@ -2181,7 +2181,16 @@ static int bch2_trans_preload_mem(struct btree_trans *trans, size_t size)
|
||||
if (size > trans->mem_bytes) {
|
||||
size_t old_bytes = trans->mem_bytes;
|
||||
size_t new_bytes = roundup_pow_of_two(size);
|
||||
void *new_mem = krealloc(trans->mem, new_bytes, GFP_NOFS);
|
||||
void *new_mem;
|
||||
|
||||
WARN_ON_ONCE(new_bytes > BTREE_TRANS_MEM_MAX);
|
||||
|
||||
new_mem = krealloc(trans->mem, new_bytes, GFP_NOFS);
|
||||
if (!new_mem && new_bytes <= BTREE_TRANS_MEM_MAX) {
|
||||
new_mem = mempool_alloc(&trans->c->btree_trans_mem_pool, GFP_KERNEL);
|
||||
new_bytes = BTREE_TRANS_MEM_MAX;
|
||||
kfree(trans->mem);
|
||||
}
|
||||
|
||||
if (!new_mem)
|
||||
return -ENOMEM;
|
||||
@ -2293,8 +2302,13 @@ void bch2_trans_init(struct btree_trans *trans, struct bch_fs *c,
|
||||
if (expected_mem_bytes) {
|
||||
expected_mem_bytes = roundup_pow_of_two(expected_mem_bytes);
|
||||
trans->mem = kmalloc(expected_mem_bytes, GFP_KERNEL);
|
||||
if (trans->mem)
|
||||
|
||||
if (!unlikely(trans->mem)) {
|
||||
trans->mem = mempool_alloc(&c->btree_trans_mem_pool, GFP_KERNEL);
|
||||
trans->mem_bytes = BTREE_TRANS_MEM_MAX;
|
||||
} else {
|
||||
trans->mem_bytes = expected_mem_bytes;
|
||||
}
|
||||
}
|
||||
|
||||
trans->srcu_idx = srcu_read_lock(&c->btree_trans_barrier);
|
||||
@ -2324,7 +2338,11 @@ int bch2_trans_exit(struct btree_trans *trans)
|
||||
bch2_journal_preres_put(&trans->c->journal, &trans->journal_preres);
|
||||
|
||||
kfree(trans->fs_usage_deltas);
|
||||
kfree(trans->mem);
|
||||
|
||||
if (trans->mem_bytes == BTREE_TRANS_MEM_MAX)
|
||||
mempool_free(trans->mem, &trans->c->btree_trans_mem_pool);
|
||||
else
|
||||
kfree(trans->mem);
|
||||
|
||||
#ifdef __KERNEL__
|
||||
/*
|
||||
@ -2332,6 +2350,7 @@ int bch2_trans_exit(struct btree_trans *trans)
|
||||
*/
|
||||
trans->iters = this_cpu_xchg(c->btree_iters_bufs->iter, trans->iters);
|
||||
#endif
|
||||
|
||||
if (trans->iters)
|
||||
mempool_free(trans->iters, &trans->c->btree_iters_pool);
|
||||
|
||||
@ -2407,6 +2426,7 @@ void bch2_btree_trans_to_text(struct printbuf *out, struct bch_fs *c)
|
||||
|
||||
void bch2_fs_btree_iter_exit(struct bch_fs *c)
|
||||
{
|
||||
mempool_exit(&c->btree_trans_mem_pool);
|
||||
mempool_exit(&c->btree_iters_pool);
|
||||
cleanup_srcu_struct(&c->btree_trans_barrier);
|
||||
}
|
||||
@ -2422,5 +2442,7 @@ int bch2_fs_btree_iter_init(struct bch_fs *c)
|
||||
mempool_init_kmalloc_pool(&c->btree_iters_pool, 1,
|
||||
sizeof(struct btree_iter) * nr +
|
||||
sizeof(struct btree_insert_entry) * nr +
|
||||
sizeof(struct btree_insert_entry) * nr);
|
||||
sizeof(struct btree_insert_entry) * nr) ?:
|
||||
mempool_init_kmalloc_pool(&c->btree_trans_mem_pool, 1,
|
||||
BTREE_TRANS_MEM_MAX);
|
||||
}
|
||||
|
@ -346,6 +346,8 @@ struct btree_insert_entry {
|
||||
#define BTREE_ITER_MAX 32
|
||||
#endif
|
||||
|
||||
#define BTREE_TRANS_MEM_MAX (1U << 14)
|
||||
|
||||
struct btree_trans {
|
||||
struct bch_fs *c;
|
||||
#ifdef CONFIG_BCACHEFS_DEBUG
|
||||
|
Loading…
x
Reference in New Issue
Block a user