diff options
Diffstat (limited to 'libbcachefs/btree_update_leaf.c')
-rw-r--r-- | libbcachefs/btree_update_leaf.c | 132 |
1 files changed, 83 insertions, 49 deletions
diff --git a/libbcachefs/btree_update_leaf.c b/libbcachefs/btree_update_leaf.c index 154a819b..a2b37dd4 100644 --- a/libbcachefs/btree_update_leaf.c +++ b/libbcachefs/btree_update_leaf.c @@ -316,15 +316,10 @@ bch2_trans_journal_preres_get_cold(struct btree_trans *trans, unsigned u64s, static __always_inline int bch2_trans_journal_res_get(struct btree_trans *trans, unsigned flags) { - struct bch_fs *c = trans->c; - int ret; - - ret = bch2_journal_res_get(&c->journal, &trans->journal_res, - trans->journal_u64s, - flags| - (trans->flags & JOURNAL_WATERMARK_MASK)); - - return ret == -EAGAIN ? BTREE_INSERT_NEED_JOURNAL_RES : ret; + return bch2_journal_res_get(&trans->c->journal, &trans->journal_res, + trans->journal_u64s, + flags| + (trans->flags & JOURNAL_WATERMARK_MASK)); } #define JSET_ENTRY_LOG_U64s 4 @@ -343,23 +338,20 @@ static void journal_transaction_name(struct btree_trans *trans) strncpy(l->d, trans->fn, JSET_ENTRY_LOG_U64s * sizeof(u64)); } -static inline enum btree_insert_ret -btree_key_can_insert(struct btree_trans *trans, - struct btree *b, - unsigned u64s) +static inline int btree_key_can_insert(struct btree_trans *trans, + struct btree *b, unsigned u64s) { struct bch_fs *c = trans->c; if (!bch2_btree_node_insert_fits(c, b, u64s)) - return BTREE_INSERT_BTREE_NODE_FULL; + return -BCH_ERR_btree_insert_btree_node_full; - return BTREE_INSERT_OK; + return 0; } -static enum btree_insert_ret -btree_key_can_insert_cached(struct btree_trans *trans, - struct btree_path *path, - unsigned u64s) +static int btree_key_can_insert_cached(struct btree_trans *trans, + struct btree_path *path, + unsigned u64s) { struct bch_fs *c = trans->c; struct bkey_cached *ck = (void *) path->l[0].b; @@ -372,7 +364,7 @@ btree_key_can_insert_cached(struct btree_trans *trans, if (!test_bit(BKEY_CACHED_DIRTY, &ck->flags) && bch2_btree_key_cache_must_wait(c) && !(trans->flags & BTREE_INSERT_JOURNAL_RECLAIM)) - return BTREE_INSERT_NEED_JOURNAL_RECLAIM; + return -BCH_ERR_btree_insert_need_journal_reclaim; /* * bch2_varint_decode can read past the end of the buffer by at most 7 @@ -381,7 +373,7 @@ btree_key_can_insert_cached(struct btree_trans *trans, u64s += 1; if (u64s <= ck->u64s) - return BTREE_INSERT_OK; + return 0; new_u64s = roundup_pow_of_two(u64s); new_k = krealloc(ck->k, new_u64s * sizeof(u64), GFP_NOFS); @@ -646,21 +638,13 @@ bch2_trans_commit_write_locked(struct btree_trans *trans, trans->journal_res.seq = c->journal.replay_journal_seq; } - if (unlikely(trans->extra_journal_entries.nr)) { - memcpy_u64s_small(journal_res_entry(&c->journal, &trans->journal_res), - trans->extra_journal_entries.data, - trans->extra_journal_entries.nr); - - trans->journal_res.offset += trans->extra_journal_entries.nr; - trans->journal_res.u64s -= trans->extra_journal_entries.nr; - } - /* * Not allowed to fail after we've gotten our journal reservation - we * have to use it: */ - if (!(trans->flags & BTREE_INSERT_JOURNAL_REPLAY)) { + if (IS_ENABLED(CONFIG_BCACHEFS_DEBUG) && + !(trans->flags & BTREE_INSERT_JOURNAL_REPLAY)) { if (bch2_journal_seq_verify) trans_for_each_update(trans, i) i->k->k.version.lo = trans->journal_res.seq; @@ -671,7 +655,7 @@ bch2_trans_commit_write_locked(struct btree_trans *trans, if (trans->fs_usage_deltas && bch2_trans_fs_usage_apply(trans, trans->fs_usage_deltas)) - return BTREE_INSERT_NEED_MARK_REPLICAS; + return -BCH_ERR_btree_insert_need_mark_replicas; trans_for_each_update(trans, i) if (BTREE_NODE_TYPE_HAS_MEM_TRIGGERS & (1U << i->bkey_type)) { @@ -686,6 +670,15 @@ bch2_trans_commit_write_locked(struct btree_trans *trans, return ret; } + if (unlikely(trans->extra_journal_entries.nr)) { + memcpy_u64s_small(journal_res_entry(&c->journal, &trans->journal_res), + trans->extra_journal_entries.data, + trans->extra_journal_entries.nr); + + trans->journal_res.offset += trans->extra_journal_entries.nr; + trans->journal_res.u64s -= trans->extra_journal_entries.nr; + } + if (likely(!(trans->flags & BTREE_INSERT_JOURNAL_REPLAY))) { trans_for_each_update(trans, i) { struct journal *j = &c->journal; @@ -844,7 +837,7 @@ static inline int do_bch2_trans_commit(struct btree_trans *trans, &trans->journal_preres, trans->journal_preres_u64s, JOURNAL_RES_GET_NONBLOCK| (trans->flags & JOURNAL_WATERMARK_MASK)); - if (unlikely(ret == -EAGAIN)) + if (unlikely(ret == -BCH_ERR_journal_preres_get_blocked)) ret = bch2_trans_journal_preres_get_cold(trans, trans->journal_preres_u64s, trace_ip); if (unlikely(ret)) @@ -900,12 +893,12 @@ int bch2_trans_commit_error(struct btree_trans *trans, struct bch_fs *c = trans->c; switch (ret) { - case BTREE_INSERT_BTREE_NODE_FULL: + case -BCH_ERR_btree_insert_btree_node_full: ret = bch2_btree_split_leaf(trans, i->path, trans->flags); if (bch2_err_matches(ret, BCH_ERR_transaction_restart)) trace_and_count(c, trans_restart_btree_node_split, trans, trace_ip, i->path); break; - case BTREE_INSERT_NEED_MARK_REPLICAS: + case -BCH_ERR_btree_insert_need_mark_replicas: bch2_trans_unlock(trans); ret = bch2_replicas_delta_list_mark(c, trans->fs_usage_deltas); @@ -916,7 +909,7 @@ int bch2_trans_commit_error(struct btree_trans *trans, if (ret) trace_and_count(c, trans_restart_mark_replicas, trans, trace_ip); break; - case BTREE_INSERT_NEED_JOURNAL_RES: + case -BCH_ERR_journal_res_get_blocked: bch2_trans_unlock(trans); if ((trans->flags & BTREE_INSERT_JOURNAL_RECLAIM) && @@ -933,7 +926,7 @@ int bch2_trans_commit_error(struct btree_trans *trans, if (ret) trace_and_count(c, trans_restart_journal_res_get, trans, trace_ip); break; - case BTREE_INSERT_NEED_JOURNAL_RECLAIM: + case -BCH_ERR_btree_insert_need_journal_reclaim: bch2_trans_unlock(trans); trace_and_count(c, trans_blocked_journal_reclaim, trans, trace_ip); @@ -970,7 +963,7 @@ bch2_trans_commit_get_rw_cold(struct btree_trans *trans) if (likely(!(trans->flags & BTREE_INSERT_LAZY_RW)) || test_bit(BCH_FS_STARTED, &c->flags)) - return -EROFS; + return -BCH_ERR_erofs_trans_commit; bch2_trans_unlock(trans); @@ -1734,18 +1727,25 @@ int bch2_btree_delete_range(struct bch_fs *c, enum btree_id id, return ret; } -int bch2_trans_log_msg(struct btree_trans *trans, const char *msg) +static int __bch2_trans_log_msg(darray_u64 *entries, const char *fmt, va_list args) { - unsigned len = strlen(msg); - unsigned u64s = DIV_ROUND_UP(len, sizeof(u64)); + struct printbuf buf = PRINTBUF; struct jset_entry_log *l; + unsigned u64s; int ret; - ret = darray_make_room(&trans->extra_journal_entries, jset_u64s(u64s)); + prt_vprintf(&buf, fmt, args); + ret = buf.allocation_failure ? -ENOMEM : 0; if (ret) - return ret; + goto err; - l = (void *) &darray_top(trans->extra_journal_entries); + u64s = DIV_ROUND_UP(buf.pos, sizeof(u64)); + + ret = darray_make_room(entries, jset_u64s(u64s)); + if (ret) + goto err; + + l = (void *) &darray_top(*entries); l->entry.u64s = cpu_to_le16(u64s); l->entry.btree_id = 0; l->entry.level = 1; @@ -1753,10 +1753,44 @@ int bch2_trans_log_msg(struct btree_trans *trans, const char *msg) l->entry.pad[0] = 0; l->entry.pad[1] = 0; l->entry.pad[2] = 0; - memcpy(l->d, msg, len); - while (len & 7) - l->d[len++] = '\0'; + memcpy(l->d, buf.buf, buf.pos); + while (buf.pos & 7) + l->d[buf.pos++] = '\0'; + + entries->nr += jset_u64s(u64s); +err: + printbuf_exit(&buf); + return ret; +} + +int bch2_trans_log_msg(struct btree_trans *trans, const char *fmt, ...) +{ + va_list args; + int ret; + + va_start(args, fmt); + ret = __bch2_trans_log_msg(&trans->extra_journal_entries, fmt, args); + va_end(args); + + return ret; +} + +int bch2_fs_log_msg(struct bch_fs *c, const char *fmt, ...) +{ + va_list args; + int ret; + + va_start(args, fmt); + + if (!test_bit(JOURNAL_STARTED, &c->journal.flags)) { + ret = __bch2_trans_log_msg(&c->journal.early_journal_entries, fmt, args); + } else { + ret = bch2_trans_do(c, NULL, NULL, BTREE_INSERT_LAZY_RW, + __bch2_trans_log_msg(&trans.extra_journal_entries, fmt, args)); + } + + va_end(args); + + return ret; - trans->extra_journal_entries.nr += jset_u64s(u64s); - return 0; } |