bcachefs: Kill BCH_WRITE_FLUSH

BCH_WRITE_FLUSH is a write flag that causes a journal flush.  It's only
used in the direct IO path, and this will allow for some consolidation
with the regular fsync path, which will help with the upcoming nocow
mode.

Signed-off-by: Kent Overstreet <kent.overstreet@linux.dev>
This commit is contained in:
Kent Overstreet 2022-11-03 00:29:43 -04:00
parent 03e83f6302
commit a1ee777bfc
6 changed files with 64 additions and 50 deletions

View file

@ -226,7 +226,7 @@ int bch2_data_update_index_update(struct bch_write_op *op)
bch2_trans_update(&trans, &iter, insert,
BTREE_UPDATE_INTERNAL_SNAPSHOT_NODE) ?:
bch2_trans_commit(&trans, &op->res,
&op->journal_seq,
NULL,
BTREE_INSERT_NOFAIL|
m->data_opts.btree_insert_flags);
if (!ret) {
@ -320,7 +320,6 @@ int bch2_data_update_init(struct bch_fs *c, struct data_update *m,
m->op.flags |= BCH_WRITE_PAGES_STABLE|
BCH_WRITE_PAGES_OWNED|
BCH_WRITE_DATA_ENCODED|
BCH_WRITE_FROM_INTERNAL|
BCH_WRITE_MOVE|
m->data_opts.write_flags;
m->op.compression_type =

View file

@ -78,6 +78,7 @@ struct dio_write {
struct mm_struct *mm;
unsigned loop:1,
sync:1,
flush:1,
free_iov:1;
struct quota_res quota_res;
u64 written;
@ -2056,6 +2057,9 @@ static noinline bool bch2_dio_write_check_allocated(struct dio_write *dio)
dio->op.opts.compression != 0);
}
static void bch2_dio_write_loop_async(struct bch_write_op *);
static __always_inline long bch2_dio_write_done(struct dio_write *dio);
/*
* We're going to return -EIOCBQUEUED, but we haven't finished consuming the
* iov_iter yet, so we need to stash a copy of the iovec: it might be on the
@ -2093,7 +2097,43 @@ static noinline int bch2_dio_write_copy_iov(struct dio_write *dio)
return 0;
}
static void bch2_dio_write_loop_async(struct bch_write_op *);
static void bch2_dio_write_flush_done(struct closure *cl)
{
struct dio_write *dio = container_of(cl, struct dio_write, op.cl);
struct bch_fs *c = dio->op.c;
closure_debug_destroy(cl);
dio->op.error = bch2_journal_error(&c->journal);
bch2_dio_write_done(dio);
}
static noinline void bch2_dio_write_flush(struct dio_write *dio)
{
struct bch_fs *c = dio->op.c;
struct bch_inode_unpacked inode;
int ret;
dio->flush = 0;
closure_init(&dio->op.cl, NULL);
if (!dio->op.error) {
ret = bch2_inode_find_by_inum(c, inode_inum(dio->inode), &inode);
if (ret)
dio->op.error = ret;
else
bch2_journal_flush_seq_async(&c->journal, inode.bi_journal_seq, &dio->op.cl);
}
if (dio->sync) {
closure_sync(&dio->op.cl);
closure_debug_destroy(&dio->op.cl);
} else {
continue_at(&dio->op.cl, bch2_dio_write_flush_done, NULL);
}
}
static __always_inline long bch2_dio_write_done(struct dio_write *dio)
{
@ -2101,13 +2141,21 @@ static __always_inline long bch2_dio_write_done(struct dio_write *dio)
struct kiocb *req = dio->req;
struct bch_inode_info *inode = dio->inode;
bool sync = dio->sync;
long ret = dio->op.error ?: ((long) dio->written << 9);
long ret;
if (unlikely(dio->flush)) {
bch2_dio_write_flush(dio);
if (!sync)
return -EIOCBQUEUED;
}
bch2_pagecache_block_put(&inode->ei_pagecache_lock);
bch2_quota_reservation_put(c, inode, &dio->quota_res);
if (dio->free_iov)
kfree(dio->iter.__iov);
ret = dio->op.error ?: ((long) dio->written << 9);
bio_put(&dio->op.wbio.bio);
/* inode->i_dio_count is our ref on inode and thus bch_fs */
@ -2215,9 +2263,6 @@ static long bch2_dio_write_loop(struct dio_write *dio)
if (sync)
dio->op.flags |= BCH_WRITE_SYNC;
if ((req->ki_flags & IOCB_DSYNC) &&
!c->opts.journal_flush_disabled)
dio->op.flags |= BCH_WRITE_FLUSH;
dio->op.flags |= BCH_WRITE_CHECK_ENOSPC;
ret = bch2_disk_reservation_get(c, &dio->op.res, bio_sectors(bio),
@ -2332,6 +2377,7 @@ ssize_t bch2_direct_write(struct kiocb *req, struct iov_iter *iter)
dio->mm = current->mm;
dio->loop = false;
dio->sync = is_sync_kiocb(req) || extending;
dio->flush = iocb_is_dsync(req) && !c->opts.journal_flush_disabled;
dio->free_iov = false;
dio->quota_res.sectors = 0;
dio->written = 0;
@ -3050,8 +3096,7 @@ static int __bchfs_fallocate(struct bch_inode_info *inode, int mode,
}
ret = bch2_extent_update(&trans, inode_inum(inode), &iter,
&reservation.k_i,
&disk_res, NULL,
&reservation.k_i, &disk_res,
0, &i_sectors_delta, true);
if (ret)
goto bkey_err;

View file

@ -273,7 +273,6 @@ int bch2_extent_update(struct btree_trans *trans,
struct btree_iter *iter,
struct bkey_i *k,
struct disk_reservation *disk_res,
u64 *journal_seq,
u64 new_i_size,
s64 *i_sectors_delta_total,
bool check_enospc)
@ -374,7 +373,7 @@ int bch2_extent_update(struct btree_trans *trans,
}
ret = bch2_trans_update(trans, iter, k, 0) ?:
bch2_trans_commit(trans, disk_res, journal_seq,
bch2_trans_commit(trans, disk_res, NULL,
BTREE_INSERT_NOCHECK_RW|
BTREE_INSERT_NOFAIL);
err:
@ -438,8 +437,7 @@ int bch2_fpunch_at(struct btree_trans *trans, struct btree_iter *iter,
bch2_cut_back(end_pos, &delete);
ret = bch2_extent_update(trans, inum, iter, &delete,
&disk_res, NULL,
0, i_sectors_delta, false);
&disk_res, 0, i_sectors_delta, false);
bch2_disk_reservation_put(c, &disk_res);
}
@ -507,7 +505,7 @@ static int bch2_write_index_default(struct bch_write_op *op)
BTREE_ITER_SLOTS|BTREE_ITER_INTENT);
ret = bch2_extent_update(&trans, inum, &iter, sk.k,
&op->res, &op->journal_seq,
&op->res,
op->new_i_size, &op->i_sectors_delta,
op->flags & BCH_WRITE_CHECK_ENOSPC);
bch2_trans_iter_exit(&trans, &iter);
@ -596,14 +594,11 @@ void bch2_submit_wbio_replicas(struct bch_write_bio *wbio, struct bch_fs *c,
static void __bch2_write(struct bch_write_op *);
static void __bch2_write_done(struct closure *cl)
static void bch2_write_done(struct closure *cl)
{
struct bch_write_op *op = container_of(cl, struct bch_write_op, cl);
struct bch_fs *c = op->c;
if (!op->error && (op->flags & BCH_WRITE_FLUSH))
op->error = bch2_journal_error(&c->journal);
bch2_disk_reservation_put(c, &op->res);
percpu_ref_put(&c->writes);
bch2_keylist_free(&op->insert_keys, op->inline_keys);
@ -616,21 +611,6 @@ static void __bch2_write_done(struct closure *cl)
op->end_io(op);
}
static __always_inline void bch2_write_done(struct bch_write_op *op)
{
if (likely(!(op->flags & BCH_WRITE_FLUSH) || op->error)) {
__bch2_write_done(&op->cl);
} else if (!(op->flags & BCH_WRITE_SYNC)) {
bch2_journal_flush_seq_async(&op->c->journal,
op->journal_seq,
&op->cl);
continue_at(&op->cl, __bch2_write_done, index_update_wq(op));
} else {
bch2_journal_flush_seq(&op->c->journal, op->journal_seq);
__bch2_write_done(&op->cl);
}
}
static noinline int bch2_write_drop_io_error_ptrs(struct bch_write_op *op)
{
struct keylist *keys = &op->insert_keys;
@ -789,16 +769,10 @@ void bch2_write_point_do_index_updates(struct work_struct *work)
__bch2_write_index(op);
if (!(op->flags & BCH_WRITE_DONE)) {
if (!(op->flags & BCH_WRITE_DONE))
__bch2_write(op);
} else if (!op->error && (op->flags & BCH_WRITE_FLUSH)) {
bch2_journal_flush_seq_async(&op->c->journal,
op->journal_seq,
&op->cl);
continue_at(&op->cl, __bch2_write_done, index_update_wq(op));
} else {
__bch2_write_done(&op->cl);
}
else
bch2_write_done(&op->cl);
}
}
@ -1347,7 +1321,7 @@ static void __bch2_write(struct bch_write_op *op)
if (!(op->flags & BCH_WRITE_DONE))
goto again;
bch2_write_done(op);
bch2_write_done(&op->cl);
} else {
continue_at(&op->cl, bch2_write_index, NULL);
}
@ -1395,7 +1369,7 @@ static void bch2_write_data_inline(struct bch_write_op *op, unsigned data_len)
__bch2_write_index(op);
err:
bch2_write_done(op);
bch2_write_done(&op->cl);
}
/**

View file

@ -31,7 +31,6 @@ const char *bch2_blk_status_to_str(blk_status_t);
enum bch_write_flags {
__BCH_WRITE_ALLOC_NOWAIT,
__BCH_WRITE_CACHED,
__BCH_WRITE_FLUSH,
__BCH_WRITE_DATA_ENCODED,
__BCH_WRITE_PAGES_STABLE,
__BCH_WRITE_PAGES_OWNED,
@ -48,7 +47,6 @@ enum bch_write_flags {
#define BCH_WRITE_ALLOC_NOWAIT (1U << __BCH_WRITE_ALLOC_NOWAIT)
#define BCH_WRITE_CACHED (1U << __BCH_WRITE_CACHED)
#define BCH_WRITE_FLUSH (1U << __BCH_WRITE_FLUSH)
#define BCH_WRITE_DATA_ENCODED (1U << __BCH_WRITE_DATA_ENCODED)
#define BCH_WRITE_PAGES_STABLE (1U << __BCH_WRITE_PAGES_STABLE)
#define BCH_WRITE_PAGES_OWNED (1U << __BCH_WRITE_PAGES_OWNED)
@ -75,7 +73,7 @@ int bch2_sum_sector_overwrites(struct btree_trans *, struct btree_iter *,
struct bkey_i *, bool *, bool *, s64 *, s64 *);
int bch2_extent_update(struct btree_trans *, subvol_inum,
struct btree_iter *, struct bkey_i *,
struct disk_reservation *, u64 *, u64, s64 *, bool);
struct disk_reservation *, u64, s64 *, bool);
int bch2_fpunch_at(struct btree_trans *, struct btree_iter *,
subvol_inum, u64, s64 *);
@ -104,7 +102,6 @@ static inline void bch2_write_op_init(struct bch_write_op *op, struct bch_fs *c,
op->version = ZERO_VERSION;
op->write_point = (struct write_point_specifier) { 0 };
op->res = (struct disk_reservation) { 0 };
op->journal_seq = 0;
op->new_i_size = U64_MAX;
op->i_sectors_delta = 0;
}

View file

@ -142,7 +142,6 @@ struct bch_write_op {
struct open_buckets open_buckets;
u64 journal_seq;
u64 new_i_size;
s64 i_sectors_delta;

View file

@ -378,7 +378,7 @@ s64 bch2_remap_range(struct bch_fs *c,
dst_end.offset - dst_iter.pos.offset));
ret = bch2_extent_update(&trans, dst_inum, &dst_iter,
new_dst.k, &disk_res, NULL,
new_dst.k, &disk_res,
new_i_size, i_sectors_delta,
true);
bch2_disk_reservation_put(c, &disk_res);