mirror of
https://github.com/koverstreet/bcachefs-tools.git
synced 2025-02-23 00:00:02 +03:00
Update bcachefs sources to 6bb1ba5c94 bcachefs: Improve alloc_mem_to_key()
This commit is contained in:
parent
2fc5a50bd6
commit
39a6bf885d
@ -1 +1 @@
|
|||||||
069e88fae5fdce2aea08c9e192cf6ac5c7ed492d
|
6bb1ba5c94c225a95cb59cb9670b558bcb1b4f81
|
||||||
|
@ -599,7 +599,7 @@ static void copy_fs(struct bch_fs *c, int src_fd, const char *src_path,
|
|||||||
darray_free(s.extents);
|
darray_free(s.extents);
|
||||||
genradix_free(&s.hardlinks);
|
genradix_free(&s.hardlinks);
|
||||||
|
|
||||||
bch2_alloc_write(c, false);
|
bch2_alloc_write_all(c, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void find_superblock_space(ranges extents,
|
static void find_superblock_space(ranges extents,
|
||||||
|
@ -38,6 +38,15 @@ static const unsigned BCH_ALLOC_V1_FIELD_BYTES[] = {
|
|||||||
#undef x
|
#undef x
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct bkey_alloc_buf {
|
||||||
|
struct bkey_i k;
|
||||||
|
struct bch_alloc_v3 v;
|
||||||
|
|
||||||
|
#define x(_name, _bits) + _bits / 8
|
||||||
|
u8 _pad[0 + BCH_ALLOC_FIELDS_V2()];
|
||||||
|
#undef x
|
||||||
|
} __attribute__((packed, aligned(8)));
|
||||||
|
|
||||||
/* Persistent alloc info: */
|
/* Persistent alloc info: */
|
||||||
|
|
||||||
static inline u64 alloc_field_v1_get(const struct bch_alloc *a,
|
static inline u64 alloc_field_v1_get(const struct bch_alloc *a,
|
||||||
@ -244,13 +253,26 @@ struct bkey_alloc_unpacked bch2_alloc_unpack(struct bkey_s_c k)
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
void bch2_alloc_pack(struct bch_fs *c,
|
static void bch2_alloc_pack(struct bch_fs *c,
|
||||||
struct bkey_alloc_buf *dst,
|
struct bkey_alloc_buf *dst,
|
||||||
const struct bkey_alloc_unpacked src)
|
const struct bkey_alloc_unpacked src)
|
||||||
{
|
{
|
||||||
bch2_alloc_pack_v3(dst, src);
|
bch2_alloc_pack_v3(dst, src);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int bch2_alloc_write(struct btree_trans *trans, struct btree_iter *iter,
|
||||||
|
struct bkey_alloc_unpacked *u, unsigned trigger_flags)
|
||||||
|
{
|
||||||
|
struct bkey_alloc_buf *a;
|
||||||
|
|
||||||
|
a = bch2_trans_kmalloc(trans, sizeof(struct bkey_alloc_buf));
|
||||||
|
if (IS_ERR(a))
|
||||||
|
return PTR_ERR(a);
|
||||||
|
|
||||||
|
bch2_alloc_pack(trans->c, a, *u);
|
||||||
|
return bch2_trans_update(trans, iter, &a->k, trigger_flags);
|
||||||
|
}
|
||||||
|
|
||||||
static unsigned bch_alloc_v1_val_u64s(const struct bch_alloc *a)
|
static unsigned bch_alloc_v1_val_u64s(const struct bch_alloc *a)
|
||||||
{
|
{
|
||||||
unsigned i, bytes = offsetof(struct bch_alloc, data);
|
unsigned i, bytes = offsetof(struct bch_alloc, data);
|
||||||
@ -371,11 +393,7 @@ static int bch2_alloc_write_key(struct btree_trans *trans,
|
|||||||
{
|
{
|
||||||
struct bch_fs *c = trans->c;
|
struct bch_fs *c = trans->c;
|
||||||
struct bkey_s_c k;
|
struct bkey_s_c k;
|
||||||
struct bch_dev *ca;
|
|
||||||
struct bucket *g;
|
|
||||||
struct bucket_mark m;
|
|
||||||
struct bkey_alloc_unpacked old_u, new_u;
|
struct bkey_alloc_unpacked old_u, new_u;
|
||||||
struct bkey_alloc_buf a;
|
|
||||||
int ret;
|
int ret;
|
||||||
retry:
|
retry:
|
||||||
bch2_trans_begin(trans);
|
bch2_trans_begin(trans);
|
||||||
@ -390,20 +408,13 @@ retry:
|
|||||||
if (ret)
|
if (ret)
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
old_u = bch2_alloc_unpack(k);
|
old_u = bch2_alloc_unpack(k);
|
||||||
|
new_u = alloc_mem_to_key(c, iter);
|
||||||
percpu_down_read(&c->mark_lock);
|
|
||||||
ca = bch_dev_bkey_exists(c, iter->pos.inode);
|
|
||||||
g = bucket(ca, iter->pos.offset);
|
|
||||||
m = READ_ONCE(g->mark);
|
|
||||||
new_u = alloc_mem_to_key(iter, g, m);
|
|
||||||
percpu_up_read(&c->mark_lock);
|
|
||||||
|
|
||||||
if (!bkey_alloc_unpacked_cmp(old_u, new_u))
|
if (!bkey_alloc_unpacked_cmp(old_u, new_u))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
bch2_alloc_pack(c, &a, new_u);
|
ret = bch2_alloc_write(trans, iter, &new_u,
|
||||||
ret = bch2_trans_update(trans, iter, &a.k,
|
|
||||||
BTREE_TRIGGER_NORUN) ?:
|
BTREE_TRIGGER_NORUN) ?:
|
||||||
bch2_trans_commit(trans, NULL, NULL,
|
bch2_trans_commit(trans, NULL, NULL,
|
||||||
BTREE_INSERT_NOFAIL|flags);
|
BTREE_INSERT_NOFAIL|flags);
|
||||||
@ -413,7 +424,7 @@ err:
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int bch2_alloc_write(struct bch_fs *c, unsigned flags)
|
int bch2_alloc_write_all(struct bch_fs *c, unsigned flags)
|
||||||
{
|
{
|
||||||
struct btree_trans trans;
|
struct btree_trans trans;
|
||||||
struct btree_iter iter;
|
struct btree_iter iter;
|
||||||
@ -450,10 +461,7 @@ int bch2_bucket_io_time_reset(struct btree_trans *trans, unsigned dev,
|
|||||||
size_t bucket_nr, int rw)
|
size_t bucket_nr, int rw)
|
||||||
{
|
{
|
||||||
struct bch_fs *c = trans->c;
|
struct bch_fs *c = trans->c;
|
||||||
struct bch_dev *ca = bch_dev_bkey_exists(c, dev);
|
|
||||||
struct btree_iter iter;
|
struct btree_iter iter;
|
||||||
struct bucket *g;
|
|
||||||
struct bkey_alloc_buf *a;
|
|
||||||
struct bkey_alloc_unpacked u;
|
struct bkey_alloc_unpacked u;
|
||||||
u64 *time, now;
|
u64 *time, now;
|
||||||
int ret = 0;
|
int ret = 0;
|
||||||
@ -466,15 +474,7 @@ int bch2_bucket_io_time_reset(struct btree_trans *trans, unsigned dev,
|
|||||||
if (ret)
|
if (ret)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
a = bch2_trans_kmalloc(trans, sizeof(struct bkey_alloc_buf));
|
u = alloc_mem_to_key(c, &iter);
|
||||||
ret = PTR_ERR_OR_ZERO(a);
|
|
||||||
if (ret)
|
|
||||||
goto out;
|
|
||||||
|
|
||||||
percpu_down_read(&c->mark_lock);
|
|
||||||
g = bucket(ca, bucket_nr);
|
|
||||||
u = alloc_mem_to_key(&iter, g, READ_ONCE(g->mark));
|
|
||||||
percpu_up_read(&c->mark_lock);
|
|
||||||
|
|
||||||
time = rw == READ ? &u.read_time : &u.write_time;
|
time = rw == READ ? &u.read_time : &u.write_time;
|
||||||
now = atomic64_read(&c->io_clock[rw].now);
|
now = atomic64_read(&c->io_clock[rw].now);
|
||||||
@ -483,8 +483,7 @@ int bch2_bucket_io_time_reset(struct btree_trans *trans, unsigned dev,
|
|||||||
|
|
||||||
*time = now;
|
*time = now;
|
||||||
|
|
||||||
bch2_alloc_pack(c, a, u);
|
ret = bch2_alloc_write(trans, &iter, &u, 0) ?:
|
||||||
ret = bch2_trans_update(trans, &iter, &a->k, 0) ?:
|
|
||||||
bch2_trans_commit(trans, NULL, NULL, 0);
|
bch2_trans_commit(trans, NULL, NULL, 0);
|
||||||
out:
|
out:
|
||||||
bch2_trans_iter_exit(trans, &iter);
|
bch2_trans_iter_exit(trans, &iter);
|
||||||
@ -752,10 +751,7 @@ static int bucket_invalidate_btree(struct btree_trans *trans,
|
|||||||
struct bch_dev *ca, u64 b)
|
struct bch_dev *ca, u64 b)
|
||||||
{
|
{
|
||||||
struct bch_fs *c = trans->c;
|
struct bch_fs *c = trans->c;
|
||||||
struct bkey_alloc_buf *a;
|
|
||||||
struct bkey_alloc_unpacked u;
|
struct bkey_alloc_unpacked u;
|
||||||
struct bucket *g;
|
|
||||||
struct bucket_mark m;
|
|
||||||
struct btree_iter iter;
|
struct btree_iter iter;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
@ -765,20 +761,11 @@ static int bucket_invalidate_btree(struct btree_trans *trans,
|
|||||||
BTREE_ITER_CACHED_NOFILL|
|
BTREE_ITER_CACHED_NOFILL|
|
||||||
BTREE_ITER_INTENT);
|
BTREE_ITER_INTENT);
|
||||||
|
|
||||||
a = bch2_trans_kmalloc(trans, sizeof(*a));
|
|
||||||
ret = PTR_ERR_OR_ZERO(a);
|
|
||||||
if (ret)
|
|
||||||
goto err;
|
|
||||||
|
|
||||||
ret = bch2_btree_iter_traverse(&iter);
|
ret = bch2_btree_iter_traverse(&iter);
|
||||||
if (ret)
|
if (ret)
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
percpu_down_read(&c->mark_lock);
|
u = alloc_mem_to_key(c, &iter);
|
||||||
g = bucket(ca, b);
|
|
||||||
m = READ_ONCE(g->mark);
|
|
||||||
u = alloc_mem_to_key(&iter, g, m);
|
|
||||||
percpu_up_read(&c->mark_lock);
|
|
||||||
|
|
||||||
u.gen++;
|
u.gen++;
|
||||||
u.data_type = 0;
|
u.data_type = 0;
|
||||||
@ -787,9 +774,8 @@ static int bucket_invalidate_btree(struct btree_trans *trans,
|
|||||||
u.read_time = atomic64_read(&c->io_clock[READ].now);
|
u.read_time = atomic64_read(&c->io_clock[READ].now);
|
||||||
u.write_time = atomic64_read(&c->io_clock[WRITE].now);
|
u.write_time = atomic64_read(&c->io_clock[WRITE].now);
|
||||||
|
|
||||||
bch2_alloc_pack(c, a, u);
|
ret = bch2_alloc_write(trans, &iter, &u,
|
||||||
ret = bch2_trans_update(trans, &iter, &a->k,
|
BTREE_TRIGGER_BUCKET_INVALIDATE);
|
||||||
BTREE_TRIGGER_BUCKET_INVALIDATE);
|
|
||||||
err:
|
err:
|
||||||
bch2_trans_iter_exit(trans, &iter);
|
bch2_trans_iter_exit(trans, &iter);
|
||||||
return ret;
|
return ret;
|
||||||
|
@ -4,7 +4,9 @@
|
|||||||
|
|
||||||
#include "bcachefs.h"
|
#include "bcachefs.h"
|
||||||
#include "alloc_types.h"
|
#include "alloc_types.h"
|
||||||
|
#include "buckets.h"
|
||||||
#include "debug.h"
|
#include "debug.h"
|
||||||
|
#include "super.h"
|
||||||
|
|
||||||
extern const char * const bch2_allocator_states[];
|
extern const char * const bch2_allocator_states[];
|
||||||
|
|
||||||
@ -20,15 +22,6 @@ struct bkey_alloc_unpacked {
|
|||||||
#undef x
|
#undef x
|
||||||
};
|
};
|
||||||
|
|
||||||
struct bkey_alloc_buf {
|
|
||||||
struct bkey_i k;
|
|
||||||
struct bch_alloc_v3 v;
|
|
||||||
|
|
||||||
#define x(_name, _bits) + _bits / 8
|
|
||||||
u8 _pad[0 + BCH_ALLOC_FIELDS_V2()];
|
|
||||||
#undef x
|
|
||||||
} __attribute__((packed, aligned(8)));
|
|
||||||
|
|
||||||
/* How out of date a pointer gen is allowed to be: */
|
/* How out of date a pointer gen is allowed to be: */
|
||||||
#define BUCKET_GC_GEN_MAX 96U
|
#define BUCKET_GC_GEN_MAX 96U
|
||||||
|
|
||||||
@ -46,28 +39,37 @@ static inline bool bkey_alloc_unpacked_cmp(struct bkey_alloc_unpacked l,
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct bkey_alloc_unpacked bch2_alloc_unpack(struct bkey_s_c);
|
struct bkey_alloc_unpacked bch2_alloc_unpack(struct bkey_s_c);
|
||||||
void bch2_alloc_pack(struct bch_fs *, struct bkey_alloc_buf *,
|
int bch2_alloc_write(struct btree_trans *, struct btree_iter *,
|
||||||
const struct bkey_alloc_unpacked);
|
struct bkey_alloc_unpacked *, unsigned);
|
||||||
|
|
||||||
int bch2_bucket_io_time_reset(struct btree_trans *, unsigned, size_t, int);
|
int bch2_bucket_io_time_reset(struct btree_trans *, unsigned, size_t, int);
|
||||||
|
|
||||||
static inline struct bkey_alloc_unpacked
|
static inline struct bkey_alloc_unpacked
|
||||||
alloc_mem_to_key(struct btree_iter *iter,
|
alloc_mem_to_key(struct bch_fs *c, struct btree_iter *iter)
|
||||||
struct bucket *g, struct bucket_mark m)
|
|
||||||
{
|
{
|
||||||
return (struct bkey_alloc_unpacked) {
|
struct bch_dev *ca;
|
||||||
|
struct bucket *g;
|
||||||
|
struct bkey_alloc_unpacked ret;
|
||||||
|
|
||||||
|
percpu_down_read(&c->mark_lock);
|
||||||
|
ca = bch_dev_bkey_exists(c, iter->pos.inode);
|
||||||
|
g = bucket(ca, iter->pos.offset);
|
||||||
|
ret = (struct bkey_alloc_unpacked) {
|
||||||
.dev = iter->pos.inode,
|
.dev = iter->pos.inode,
|
||||||
.bucket = iter->pos.offset,
|
.bucket = iter->pos.offset,
|
||||||
.gen = m.gen,
|
.gen = g->mark.gen,
|
||||||
.oldest_gen = g->oldest_gen,
|
.oldest_gen = g->oldest_gen,
|
||||||
.data_type = m.data_type,
|
.data_type = g->mark.data_type,
|
||||||
.dirty_sectors = m.dirty_sectors,
|
.dirty_sectors = g->mark.dirty_sectors,
|
||||||
.cached_sectors = m.cached_sectors,
|
.cached_sectors = g->mark.cached_sectors,
|
||||||
.read_time = g->io_time[READ],
|
.read_time = g->io_time[READ],
|
||||||
.write_time = g->io_time[WRITE],
|
.write_time = g->io_time[WRITE],
|
||||||
.stripe = g->stripe,
|
.stripe = g->stripe,
|
||||||
.stripe_redundancy = g->stripe_redundancy,
|
.stripe_redundancy = g->stripe_redundancy,
|
||||||
};
|
};
|
||||||
|
percpu_up_read(&c->mark_lock);
|
||||||
|
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
#define ALLOC_SCAN_BATCH(ca) max_t(size_t, 1, (ca)->mi.nbuckets >> 9)
|
#define ALLOC_SCAN_BATCH(ca) max_t(size_t, 1, (ca)->mi.nbuckets >> 9)
|
||||||
@ -137,7 +139,7 @@ void bch2_dev_allocator_quiesce(struct bch_fs *, struct bch_dev *);
|
|||||||
void bch2_dev_allocator_stop(struct bch_dev *);
|
void bch2_dev_allocator_stop(struct bch_dev *);
|
||||||
int bch2_dev_allocator_start(struct bch_dev *);
|
int bch2_dev_allocator_start(struct bch_dev *);
|
||||||
|
|
||||||
int bch2_alloc_write(struct bch_fs *, unsigned);
|
int bch2_alloc_write_all(struct bch_fs *, unsigned);
|
||||||
void bch2_fs_allocator_background_init(struct bch_fs *);
|
void bch2_fs_allocator_background_init(struct bch_fs *);
|
||||||
|
|
||||||
void bch2_open_buckets_to_text(struct printbuf *, struct bch_fs *);
|
void bch2_open_buckets_to_text(struct printbuf *, struct bch_fs *);
|
||||||
|
@ -321,8 +321,12 @@ BCH_DEBUG_PARAMS_DEBUG()
|
|||||||
#define BCH_TIME_STATS() \
|
#define BCH_TIME_STATS() \
|
||||||
x(btree_node_mem_alloc) \
|
x(btree_node_mem_alloc) \
|
||||||
x(btree_node_split) \
|
x(btree_node_split) \
|
||||||
|
x(btree_node_compact) \
|
||||||
|
x(btree_node_merge) \
|
||||||
x(btree_node_sort) \
|
x(btree_node_sort) \
|
||||||
x(btree_node_read) \
|
x(btree_node_read) \
|
||||||
|
x(btree_interior_update_foreground) \
|
||||||
|
x(btree_interior_update_total) \
|
||||||
x(btree_gc) \
|
x(btree_gc) \
|
||||||
x(btree_lock_contended_read) \
|
x(btree_lock_contended_read) \
|
||||||
x(btree_lock_contended_intent) \
|
x(btree_lock_contended_intent) \
|
||||||
@ -330,8 +334,8 @@ BCH_DEBUG_PARAMS_DEBUG()
|
|||||||
x(data_write) \
|
x(data_write) \
|
||||||
x(data_read) \
|
x(data_read) \
|
||||||
x(data_promote) \
|
x(data_promote) \
|
||||||
x(journal_write) \
|
x(journal_flush_write) \
|
||||||
x(journal_delay) \
|
x(journal_noflush_write) \
|
||||||
x(journal_flush_seq) \
|
x(journal_flush_seq) \
|
||||||
x(blocked_journal) \
|
x(blocked_journal) \
|
||||||
x(blocked_allocate) \
|
x(blocked_allocate) \
|
||||||
|
@ -1849,6 +1849,7 @@ int bch2_gc_gens(struct bch_fs *c)
|
|||||||
struct bch_dev *ca;
|
struct bch_dev *ca;
|
||||||
struct bucket_array *buckets;
|
struct bucket_array *buckets;
|
||||||
struct bucket *g;
|
struct bucket *g;
|
||||||
|
u64 start_time = local_clock();
|
||||||
unsigned i;
|
unsigned i;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
@ -1892,6 +1893,8 @@ int bch2_gc_gens(struct bch_fs *c)
|
|||||||
c->gc_gens_pos = POS_MIN;
|
c->gc_gens_pos = POS_MIN;
|
||||||
|
|
||||||
c->gc_count++;
|
c->gc_count++;
|
||||||
|
|
||||||
|
bch2_time_stats_update(&c->times[BCH_TIME_btree_gc], start_time);
|
||||||
err:
|
err:
|
||||||
up_read(&c->gc_lock);
|
up_read(&c->gc_lock);
|
||||||
return ret;
|
return ret;
|
||||||
|
@ -455,15 +455,23 @@ static void bch2_btree_update_free(struct btree_update *as)
|
|||||||
bch2_disk_reservation_put(c, &as->disk_res);
|
bch2_disk_reservation_put(c, &as->disk_res);
|
||||||
bch2_btree_reserve_put(as);
|
bch2_btree_reserve_put(as);
|
||||||
|
|
||||||
|
bch2_time_stats_update(&c->times[BCH_TIME_btree_interior_update_total],
|
||||||
|
as->start_time);
|
||||||
|
|
||||||
mutex_lock(&c->btree_interior_update_lock);
|
mutex_lock(&c->btree_interior_update_lock);
|
||||||
list_del(&as->unwritten_list);
|
list_del(&as->unwritten_list);
|
||||||
list_del(&as->list);
|
list_del(&as->list);
|
||||||
mutex_unlock(&c->btree_interior_update_lock);
|
|
||||||
|
|
||||||
closure_debug_destroy(&as->cl);
|
closure_debug_destroy(&as->cl);
|
||||||
mempool_free(as, &c->btree_interior_update_pool);
|
mempool_free(as, &c->btree_interior_update_pool);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Have to do the wakeup with btree_interior_update_lock still held,
|
||||||
|
* since being on btree_interior_update_list is our ref on @c:
|
||||||
|
*/
|
||||||
closure_wake_up(&c->btree_interior_update_wait);
|
closure_wake_up(&c->btree_interior_update_wait);
|
||||||
|
|
||||||
|
mutex_unlock(&c->btree_interior_update_lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void btree_update_will_delete_key(struct btree_update *as,
|
static void btree_update_will_delete_key(struct btree_update *as,
|
||||||
@ -902,6 +910,9 @@ static void bch2_btree_interior_update_will_free_node(struct btree_update *as,
|
|||||||
|
|
||||||
static void bch2_btree_update_done(struct btree_update *as)
|
static void bch2_btree_update_done(struct btree_update *as)
|
||||||
{
|
{
|
||||||
|
struct bch_fs *c = as->c;
|
||||||
|
u64 start_time = as->start_time;
|
||||||
|
|
||||||
BUG_ON(as->mode == BTREE_INTERIOR_NO_UPDATE);
|
BUG_ON(as->mode == BTREE_INTERIOR_NO_UPDATE);
|
||||||
|
|
||||||
if (as->took_gc_lock)
|
if (as->took_gc_lock)
|
||||||
@ -912,6 +923,9 @@ static void bch2_btree_update_done(struct btree_update *as)
|
|||||||
|
|
||||||
continue_at(&as->cl, btree_update_set_nodes_written,
|
continue_at(&as->cl, btree_update_set_nodes_written,
|
||||||
as->c->btree_interior_update_worker);
|
as->c->btree_interior_update_worker);
|
||||||
|
|
||||||
|
bch2_time_stats_update(&c->times[BCH_TIME_btree_interior_update_foreground],
|
||||||
|
start_time);
|
||||||
}
|
}
|
||||||
|
|
||||||
static struct btree_update *
|
static struct btree_update *
|
||||||
@ -921,6 +935,7 @@ bch2_btree_update_start(struct btree_trans *trans, struct btree_path *path,
|
|||||||
struct bch_fs *c = trans->c;
|
struct bch_fs *c = trans->c;
|
||||||
struct btree_update *as;
|
struct btree_update *as;
|
||||||
struct closure cl;
|
struct closure cl;
|
||||||
|
u64 start_time = local_clock();
|
||||||
int disk_res_flags = (flags & BTREE_INSERT_NOFAIL)
|
int disk_res_flags = (flags & BTREE_INSERT_NOFAIL)
|
||||||
? BCH_DISK_RESERVATION_NOFAIL : 0;
|
? BCH_DISK_RESERVATION_NOFAIL : 0;
|
||||||
int journal_flags = 0;
|
int journal_flags = 0;
|
||||||
@ -960,6 +975,7 @@ retry:
|
|||||||
memset(as, 0, sizeof(*as));
|
memset(as, 0, sizeof(*as));
|
||||||
closure_init(&as->cl, NULL);
|
closure_init(&as->cl, NULL);
|
||||||
as->c = c;
|
as->c = c;
|
||||||
|
as->start_time = start_time;
|
||||||
as->mode = BTREE_INTERIOR_NO_UPDATE;
|
as->mode = BTREE_INTERIOR_NO_UPDATE;
|
||||||
as->took_gc_lock = !(flags & BTREE_INSERT_GC_LOCK_HELD);
|
as->took_gc_lock = !(flags & BTREE_INSERT_GC_LOCK_HELD);
|
||||||
as->btree_id = path->btree_id;
|
as->btree_id = path->btree_id;
|
||||||
@ -1452,7 +1468,9 @@ static void btree_split(struct btree_update *as, struct btree_trans *trans,
|
|||||||
|
|
||||||
bch2_trans_verify_locks(trans);
|
bch2_trans_verify_locks(trans);
|
||||||
|
|
||||||
bch2_time_stats_update(&c->times[BCH_TIME_btree_node_split],
|
bch2_time_stats_update(&c->times[n2
|
||||||
|
? BCH_TIME_btree_node_split
|
||||||
|
: BCH_TIME_btree_node_compact],
|
||||||
start_time);
|
start_time);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1573,6 +1591,7 @@ int __bch2_foreground_maybe_merge(struct btree_trans *trans,
|
|||||||
struct btree *b, *m, *n, *prev, *next, *parent;
|
struct btree *b, *m, *n, *prev, *next, *parent;
|
||||||
struct bpos sib_pos;
|
struct bpos sib_pos;
|
||||||
size_t sib_u64s;
|
size_t sib_u64s;
|
||||||
|
u64 start_time = local_clock();
|
||||||
int ret = 0;
|
int ret = 0;
|
||||||
|
|
||||||
BUG_ON(!path->should_be_locked);
|
BUG_ON(!path->should_be_locked);
|
||||||
@ -1710,6 +1729,8 @@ int __bch2_foreground_maybe_merge(struct btree_trans *trans,
|
|||||||
six_unlock_intent(&n->c.lock);
|
six_unlock_intent(&n->c.lock);
|
||||||
|
|
||||||
bch2_btree_update_done(as);
|
bch2_btree_update_done(as);
|
||||||
|
|
||||||
|
bch2_time_stats_update(&c->times[BCH_TIME_btree_node_merge], start_time);
|
||||||
out:
|
out:
|
||||||
err:
|
err:
|
||||||
bch2_path_put(trans, sib_path, true);
|
bch2_path_put(trans, sib_path, true);
|
||||||
|
@ -35,6 +35,7 @@ bool bch2_btree_node_format_fits(struct bch_fs *c, struct btree *,
|
|||||||
struct btree_update {
|
struct btree_update {
|
||||||
struct closure cl;
|
struct closure cl;
|
||||||
struct bch_fs *c;
|
struct bch_fs *c;
|
||||||
|
u64 start_time;
|
||||||
|
|
||||||
struct list_head list;
|
struct list_head list;
|
||||||
struct list_head unwritten_list;
|
struct list_head unwritten_list;
|
||||||
|
@ -1440,6 +1440,8 @@ retry:
|
|||||||
(k = bch2_btree_iter_peek(&iter)).k) &&
|
(k = bch2_btree_iter_peek(&iter)).k) &&
|
||||||
!(ret = bkey_err(k)) &&
|
!(ret = bkey_err(k)) &&
|
||||||
bkey_cmp(iter.pos, end) < 0) {
|
bkey_cmp(iter.pos, end) < 0) {
|
||||||
|
struct disk_reservation disk_res =
|
||||||
|
bch2_disk_reservation_init(trans->c, 0);
|
||||||
struct bkey_i delete;
|
struct bkey_i delete;
|
||||||
|
|
||||||
bkey_init(&delete.k);
|
bkey_init(&delete.k);
|
||||||
@ -1474,8 +1476,9 @@ retry:
|
|||||||
}
|
}
|
||||||
|
|
||||||
ret = bch2_trans_update(trans, &iter, &delete, 0) ?:
|
ret = bch2_trans_update(trans, &iter, &delete, 0) ?:
|
||||||
bch2_trans_commit(trans, NULL, journal_seq,
|
bch2_trans_commit(trans, &disk_res, journal_seq,
|
||||||
BTREE_INSERT_NOFAIL);
|
BTREE_INSERT_NOFAIL);
|
||||||
|
bch2_disk_reservation_put(trans->c, &disk_res);
|
||||||
if (ret)
|
if (ret)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -977,7 +977,6 @@ static int bch2_mark_stripe_ptr(struct btree_trans *trans,
|
|||||||
update_replicas(c, k, &r.e, sectors, trans->journal_res.seq, gc);
|
update_replicas(c, k, &r.e, sectors, trans->journal_res.seq, gc);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1123,7 +1122,6 @@ static int bch2_mark_stripe(struct btree_trans *trans,
|
|||||||
*/
|
*/
|
||||||
m->alive = true;
|
m->alive = true;
|
||||||
m->sectors = le16_to_cpu(new_s->sectors);
|
m->sectors = le16_to_cpu(new_s->sectors);
|
||||||
m->algorithm = new_s->algorithm;
|
|
||||||
m->nr_blocks = new_s->nr_blocks;
|
m->nr_blocks = new_s->nr_blocks;
|
||||||
m->nr_redundant = new_s->nr_redundant;
|
m->nr_redundant = new_s->nr_redundant;
|
||||||
|
|
||||||
@ -1483,23 +1481,16 @@ need_mark:
|
|||||||
|
|
||||||
/* trans_mark: */
|
/* trans_mark: */
|
||||||
|
|
||||||
static struct bkey_alloc_buf *
|
static int bch2_trans_start_alloc_update(struct btree_trans *trans, struct btree_iter *iter,
|
||||||
bch2_trans_start_alloc_update(struct btree_trans *trans, struct btree_iter *iter,
|
|
||||||
const struct bch_extent_ptr *ptr,
|
const struct bch_extent_ptr *ptr,
|
||||||
struct bkey_alloc_unpacked *u)
|
struct bkey_alloc_unpacked *u)
|
||||||
{
|
{
|
||||||
struct bch_fs *c = trans->c;
|
struct bch_fs *c = trans->c;
|
||||||
struct bch_dev *ca = bch_dev_bkey_exists(c, ptr->dev);
|
struct bch_dev *ca = bch_dev_bkey_exists(c, ptr->dev);
|
||||||
struct bpos pos = POS(ptr->dev, PTR_BUCKET_NR(ca, ptr));
|
struct bpos pos = POS(ptr->dev, PTR_BUCKET_NR(ca, ptr));
|
||||||
struct bucket *g;
|
|
||||||
struct bkey_alloc_buf *a;
|
|
||||||
struct bkey_i *update = btree_trans_peek_updates(trans, BTREE_ID_alloc, pos);
|
struct bkey_i *update = btree_trans_peek_updates(trans, BTREE_ID_alloc, pos);
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
a = bch2_trans_kmalloc(trans, sizeof(struct bkey_alloc_buf));
|
|
||||||
if (IS_ERR(a))
|
|
||||||
return a;
|
|
||||||
|
|
||||||
bch2_trans_iter_init(trans, iter, BTREE_ID_alloc, pos,
|
bch2_trans_iter_init(trans, iter, BTREE_ID_alloc, pos,
|
||||||
BTREE_ITER_CACHED|
|
BTREE_ITER_CACHED|
|
||||||
BTREE_ITER_CACHED_NOFILL|
|
BTREE_ITER_CACHED_NOFILL|
|
||||||
@ -1507,34 +1498,27 @@ bch2_trans_start_alloc_update(struct btree_trans *trans, struct btree_iter *iter
|
|||||||
ret = bch2_btree_iter_traverse(iter);
|
ret = bch2_btree_iter_traverse(iter);
|
||||||
if (ret) {
|
if (ret) {
|
||||||
bch2_trans_iter_exit(trans, iter);
|
bch2_trans_iter_exit(trans, iter);
|
||||||
return ERR_PTR(ret);
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (update && !bpos_cmp(update->k.p, pos)) {
|
*u = update && !bpos_cmp(update->k.p, pos)
|
||||||
*u = bch2_alloc_unpack(bkey_i_to_s_c(update));
|
? bch2_alloc_unpack(bkey_i_to_s_c(update))
|
||||||
} else {
|
: alloc_mem_to_key(c, iter);
|
||||||
percpu_down_read(&c->mark_lock);
|
|
||||||
g = bucket(ca, pos.offset);
|
|
||||||
*u = alloc_mem_to_key(iter, g, READ_ONCE(g->mark));
|
|
||||||
percpu_up_read(&c->mark_lock);
|
|
||||||
}
|
|
||||||
|
|
||||||
return a;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int bch2_trans_mark_pointer(struct btree_trans *trans,
|
static int bch2_trans_mark_pointer(struct btree_trans *trans,
|
||||||
struct bkey_s_c k, struct extent_ptr_decoded p,
|
struct bkey_s_c k, struct extent_ptr_decoded p,
|
||||||
s64 sectors, enum bch_data_type data_type)
|
s64 sectors, enum bch_data_type data_type)
|
||||||
{
|
{
|
||||||
struct bch_fs *c = trans->c;
|
|
||||||
struct btree_iter iter;
|
struct btree_iter iter;
|
||||||
struct bkey_alloc_unpacked u;
|
struct bkey_alloc_unpacked u;
|
||||||
struct bkey_alloc_buf *a;
|
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
a = bch2_trans_start_alloc_update(trans, &iter, &p.ptr, &u);
|
ret = bch2_trans_start_alloc_update(trans, &iter, &p.ptr, &u);
|
||||||
if (IS_ERR(a))
|
if (ret)
|
||||||
return PTR_ERR(a);
|
return ret;
|
||||||
|
|
||||||
ret = __mark_pointer(trans, k, &p.ptr, sectors, data_type,
|
ret = __mark_pointer(trans, k, &p.ptr, sectors, data_type,
|
||||||
u.gen, &u.data_type,
|
u.gen, &u.data_type,
|
||||||
@ -1542,8 +1526,7 @@ static int bch2_trans_mark_pointer(struct btree_trans *trans,
|
|||||||
if (ret)
|
if (ret)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
bch2_alloc_pack(c, a, u);
|
ret = bch2_alloc_write(trans, &iter, &u, 0);
|
||||||
ret = bch2_trans_update(trans, &iter, &a->k, 0);
|
|
||||||
if (ret)
|
if (ret)
|
||||||
goto out;
|
goto out;
|
||||||
out:
|
out:
|
||||||
@ -1673,7 +1656,6 @@ static int bch2_trans_mark_stripe_bucket(struct btree_trans *trans,
|
|||||||
{
|
{
|
||||||
struct bch_fs *c = trans->c;
|
struct bch_fs *c = trans->c;
|
||||||
const struct bch_extent_ptr *ptr = &s.v->ptrs[idx];
|
const struct bch_extent_ptr *ptr = &s.v->ptrs[idx];
|
||||||
struct bkey_alloc_buf *a;
|
|
||||||
struct btree_iter iter;
|
struct btree_iter iter;
|
||||||
struct bkey_alloc_unpacked u;
|
struct bkey_alloc_unpacked u;
|
||||||
enum bch_data_type data_type = idx >= s.v->nr_blocks - s.v->nr_redundant
|
enum bch_data_type data_type = idx >= s.v->nr_blocks - s.v->nr_redundant
|
||||||
@ -1684,9 +1666,9 @@ static int bch2_trans_mark_stripe_bucket(struct btree_trans *trans,
|
|||||||
if (deleting)
|
if (deleting)
|
||||||
sectors = -sectors;
|
sectors = -sectors;
|
||||||
|
|
||||||
a = bch2_trans_start_alloc_update(trans, &iter, ptr, &u);
|
ret = bch2_trans_start_alloc_update(trans, &iter, ptr, &u);
|
||||||
if (IS_ERR(a))
|
if (ret)
|
||||||
return PTR_ERR(a);
|
return ret;
|
||||||
|
|
||||||
ret = check_bucket_ref(c, s.s_c, ptr, sectors, data_type,
|
ret = check_bucket_ref(c, s.s_c, ptr, sectors, data_type,
|
||||||
u.gen, u.data_type,
|
u.gen, u.data_type,
|
||||||
@ -1736,8 +1718,7 @@ static int bch2_trans_mark_stripe_bucket(struct btree_trans *trans,
|
|||||||
if (data_type)
|
if (data_type)
|
||||||
u.data_type = !deleting ? data_type : 0;
|
u.data_type = !deleting ? data_type : 0;
|
||||||
|
|
||||||
bch2_alloc_pack(c, a, u);
|
ret = bch2_alloc_write(trans, &iter, &u, 0);
|
||||||
ret = bch2_trans_update(trans, &iter, &a->k, 0);
|
|
||||||
if (ret)
|
if (ret)
|
||||||
goto err;
|
goto err;
|
||||||
err:
|
err:
|
||||||
@ -1985,7 +1966,6 @@ static int __bch2_trans_mark_metadata_bucket(struct btree_trans *trans,
|
|||||||
struct bch_fs *c = trans->c;
|
struct bch_fs *c = trans->c;
|
||||||
struct btree_iter iter;
|
struct btree_iter iter;
|
||||||
struct bkey_alloc_unpacked u;
|
struct bkey_alloc_unpacked u;
|
||||||
struct bkey_alloc_buf *a;
|
|
||||||
struct bch_extent_ptr ptr = {
|
struct bch_extent_ptr ptr = {
|
||||||
.dev = ca->dev_idx,
|
.dev = ca->dev_idx,
|
||||||
.offset = bucket_to_sector(ca, b),
|
.offset = bucket_to_sector(ca, b),
|
||||||
@ -1998,9 +1978,9 @@ static int __bch2_trans_mark_metadata_bucket(struct btree_trans *trans,
|
|||||||
if (b >= ca->mi.nbuckets)
|
if (b >= ca->mi.nbuckets)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
a = bch2_trans_start_alloc_update(trans, &iter, &ptr, &u);
|
ret = bch2_trans_start_alloc_update(trans, &iter, &ptr, &u);
|
||||||
if (IS_ERR(a))
|
if (ret)
|
||||||
return PTR_ERR(a);
|
return ret;
|
||||||
|
|
||||||
if (u.data_type && u.data_type != type) {
|
if (u.data_type && u.data_type != type) {
|
||||||
bch2_fsck_err(c, FSCK_CAN_IGNORE|FSCK_NEED_FSCK,
|
bch2_fsck_err(c, FSCK_CAN_IGNORE|FSCK_NEED_FSCK,
|
||||||
@ -2017,8 +1997,7 @@ static int __bch2_trans_mark_metadata_bucket(struct btree_trans *trans,
|
|||||||
u.data_type = type;
|
u.data_type = type;
|
||||||
u.dirty_sectors = sectors;
|
u.dirty_sectors = sectors;
|
||||||
|
|
||||||
bch2_alloc_pack(c, a, u);
|
ret = bch2_alloc_write(trans, &iter, &u, 0);
|
||||||
ret = bch2_trans_update(trans, &iter, &a->k, 0);
|
|
||||||
if (ret)
|
if (ret)
|
||||||
goto out;
|
goto out;
|
||||||
out:
|
out:
|
||||||
|
@ -143,8 +143,8 @@ void bch2_stripe_to_text(struct printbuf *out, struct bch_fs *c,
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* returns blocknr in stripe that we matched: */
|
/* returns blocknr in stripe that we matched: */
|
||||||
static int bkey_matches_stripe(struct bch_stripe *s,
|
static const struct bch_extent_ptr *bkey_matches_stripe(struct bch_stripe *s,
|
||||||
struct bkey_s_c k)
|
struct bkey_s_c k, unsigned *block)
|
||||||
{
|
{
|
||||||
struct bkey_ptrs_c ptrs = bch2_bkey_ptrs_c(k);
|
struct bkey_ptrs_c ptrs = bch2_bkey_ptrs_c(k);
|
||||||
const struct bch_extent_ptr *ptr;
|
const struct bch_extent_ptr *ptr;
|
||||||
@ -153,10 +153,12 @@ static int bkey_matches_stripe(struct bch_stripe *s,
|
|||||||
bkey_for_each_ptr(ptrs, ptr)
|
bkey_for_each_ptr(ptrs, ptr)
|
||||||
for (i = 0; i < nr_data; i++)
|
for (i = 0; i < nr_data; i++)
|
||||||
if (__bch2_ptr_matches_stripe(&s->ptrs[i], ptr,
|
if (__bch2_ptr_matches_stripe(&s->ptrs[i], ptr,
|
||||||
le16_to_cpu(s->sectors)))
|
le16_to_cpu(s->sectors))) {
|
||||||
return i;
|
*block = i;
|
||||||
|
return ptr;
|
||||||
|
}
|
||||||
|
|
||||||
return -1;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool extent_has_stripe_ptr(struct bkey_s_c k, u64 idx)
|
static bool extent_has_stripe_ptr(struct bkey_s_c k, u64 idx)
|
||||||
@ -834,6 +836,7 @@ retry:
|
|||||||
(k = bch2_btree_iter_peek(&iter)).k &&
|
(k = bch2_btree_iter_peek(&iter)).k &&
|
||||||
!(ret = bkey_err(k)) &&
|
!(ret = bkey_err(k)) &&
|
||||||
bkey_cmp(bkey_start_pos(k.k), pos->p) < 0) {
|
bkey_cmp(bkey_start_pos(k.k), pos->p) < 0) {
|
||||||
|
const struct bch_extent_ptr *ptr_c;
|
||||||
struct bch_extent_ptr *ptr, *ec_ptr = NULL;
|
struct bch_extent_ptr *ptr, *ec_ptr = NULL;
|
||||||
|
|
||||||
if (extent_has_stripe_ptr(k, s->key.k.p.offset)) {
|
if (extent_has_stripe_ptr(k, s->key.k.p.offset)) {
|
||||||
@ -841,8 +844,12 @@ retry:
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
block = bkey_matches_stripe(&s->key.v, k);
|
ptr_c = bkey_matches_stripe(&s->key.v, k, &block);
|
||||||
if (block < 0) {
|
/*
|
||||||
|
* It doesn't generally make sense to erasure code cached ptrs:
|
||||||
|
* XXX: should we be incrementing a counter?
|
||||||
|
*/
|
||||||
|
if (!ptr_c || ptr_c->cached) {
|
||||||
bch2_btree_iter_advance(&iter);
|
bch2_btree_iter_advance(&iter);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -25,7 +25,6 @@ struct stripe {
|
|||||||
|
|
||||||
struct gc_stripe {
|
struct gc_stripe {
|
||||||
u16 sectors;
|
u16 sectors;
|
||||||
u8 algorithm;
|
|
||||||
|
|
||||||
u8 nr_blocks;
|
u8 nr_blocks;
|
||||||
u8 nr_redundant;
|
u8 nr_redundant;
|
||||||
|
@ -329,6 +329,7 @@ bool bch2_reinherit_attrs(struct bch_inode_unpacked *dst_u,
|
|||||||
bool ret = false;
|
bool ret = false;
|
||||||
|
|
||||||
for (id = 0; id < Inode_opt_nr; id++) {
|
for (id = 0; id < Inode_opt_nr; id++) {
|
||||||
|
/* Skip attributes that were explicitly set on this inode */
|
||||||
if (dst_u->bi_fields_set & (1 << id))
|
if (dst_u->bi_fields_set & (1 << id))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -1280,7 +1280,7 @@ static void bch2_writepage_io_done(struct closure *cl)
|
|||||||
* racing with fallocate can cause us to add fewer sectors than
|
* racing with fallocate can cause us to add fewer sectors than
|
||||||
* expected - but we shouldn't add more sectors than expected:
|
* expected - but we shouldn't add more sectors than expected:
|
||||||
*/
|
*/
|
||||||
BUG_ON(io->op.i_sectors_delta > 0);
|
WARN_ON(io->op.i_sectors_delta > 0);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* (error (due to going RO) halfway through a page can screw that up
|
* (error (due to going RO) halfway through a page can screw that up
|
||||||
|
@ -1111,7 +1111,7 @@ again:
|
|||||||
*/
|
*/
|
||||||
wp = bch2_alloc_sectors_start(c,
|
wp = bch2_alloc_sectors_start(c,
|
||||||
op->target,
|
op->target,
|
||||||
op->opts.erasure_code,
|
op->opts.erasure_code && !(op->flags & BCH_WRITE_CACHED),
|
||||||
op->write_point,
|
op->write_point,
|
||||||
&op->devs_have,
|
&op->devs_have,
|
||||||
op->nr_replicas,
|
op->nr_replicas,
|
||||||
|
@ -626,6 +626,12 @@ int bch2_journal_flush_seq(struct journal *j, u64 seq)
|
|||||||
u64 start_time = local_clock();
|
u64 start_time = local_clock();
|
||||||
int ret, ret2;
|
int ret, ret2;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Don't update time_stats when @seq is already flushed:
|
||||||
|
*/
|
||||||
|
if (seq <= j->flushed_seq_ondisk)
|
||||||
|
return 0;
|
||||||
|
|
||||||
ret = wait_event_interruptible(j->wait, (ret2 = bch2_journal_flush_seq_async(j, seq, NULL)));
|
ret = wait_event_interruptible(j->wait, (ret2 = bch2_journal_flush_seq_async(j, seq, NULL)));
|
||||||
|
|
||||||
if (!ret)
|
if (!ret)
|
||||||
|
@ -1238,7 +1238,9 @@ static void journal_write_done(struct closure *cl)
|
|||||||
u64 v, seq;
|
u64 v, seq;
|
||||||
int err = 0;
|
int err = 0;
|
||||||
|
|
||||||
bch2_time_stats_update(j->write_time, j->write_start_time);
|
bch2_time_stats_update(!JSET_NO_FLUSH(w->data)
|
||||||
|
? j->flush_write_time
|
||||||
|
: j->noflush_write_time, j->write_start_time);
|
||||||
|
|
||||||
if (!w->devs_written.nr) {
|
if (!w->devs_written.nr) {
|
||||||
bch_err(c, "unable to write journal to sufficient devices");
|
bch_err(c, "unable to write journal to sufficient devices");
|
||||||
|
@ -271,8 +271,8 @@ struct journal {
|
|||||||
u64 nr_flush_writes;
|
u64 nr_flush_writes;
|
||||||
u64 nr_noflush_writes;
|
u64 nr_noflush_writes;
|
||||||
|
|
||||||
struct time_stats *write_time;
|
struct time_stats *flush_write_time;
|
||||||
struct time_stats *delay_time;
|
struct time_stats *noflush_write_time;
|
||||||
struct time_stats *blocked_time;
|
struct time_stats *blocked_time;
|
||||||
struct time_stats *flush_seq_time;
|
struct time_stats *flush_seq_time;
|
||||||
|
|
||||||
|
@ -394,10 +394,14 @@ int bch2_migrate_write_init(struct bch_fs *c, struct migrate_write *m,
|
|||||||
unsigned compressed_sectors = 0;
|
unsigned compressed_sectors = 0;
|
||||||
|
|
||||||
bkey_for_each_ptr_decode(k.k, ptrs, p, entry)
|
bkey_for_each_ptr_decode(k.k, ptrs, p, entry)
|
||||||
if (p.ptr.dev == data_opts.rewrite_dev &&
|
if (p.ptr.dev == data_opts.rewrite_dev) {
|
||||||
!p.ptr.cached &&
|
if (p.ptr.cached)
|
||||||
crc_is_compressed(p.crc))
|
m->op.flags |= BCH_WRITE_CACHED;
|
||||||
compressed_sectors += p.crc.compressed_size;
|
|
||||||
|
if (!p.ptr.cached &&
|
||||||
|
crc_is_compressed(p.crc))
|
||||||
|
compressed_sectors += p.crc.compressed_size;
|
||||||
|
}
|
||||||
|
|
||||||
if (compressed_sectors) {
|
if (compressed_sectors) {
|
||||||
ret = bch2_disk_reservation_add(c, &m->op.res,
|
ret = bch2_disk_reservation_add(c, &m->op.res,
|
||||||
|
@ -291,7 +291,7 @@ void bch2_opt_to_text(struct printbuf *out, struct bch_fs *c,
|
|||||||
pr_buf(out, "%lli", v);
|
pr_buf(out, "%lli", v);
|
||||||
break;
|
break;
|
||||||
case BCH_OPT_SECTORS:
|
case BCH_OPT_SECTORS:
|
||||||
bch2_hprint(out, v);
|
bch2_hprint(out, v << 9);
|
||||||
break;
|
break;
|
||||||
case BCH_OPT_STR:
|
case BCH_OPT_STR:
|
||||||
if (flags & OPT_SHOW_FULL_LIST)
|
if (flags & OPT_SHOW_FULL_LIST)
|
||||||
|
@ -81,9 +81,9 @@ enum opt_type {
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#ifdef __KERNEL__
|
#ifdef __KERNEL__
|
||||||
#define RATELIMIT_ERRORS true
|
#define RATELIMIT_ERRORS_DEFAULT true
|
||||||
#else
|
#else
|
||||||
#define RATELIMIT_ERRORS false
|
#define RATELIMIT_ERRORS_DEFAULT false
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define BCH_OPTS() \
|
#define BCH_OPTS() \
|
||||||
@ -288,7 +288,7 @@ enum opt_type {
|
|||||||
x(ratelimit_errors, u8, \
|
x(ratelimit_errors, u8, \
|
||||||
OPT_FS|OPT_MOUNT, \
|
OPT_FS|OPT_MOUNT, \
|
||||||
OPT_BOOL(), \
|
OPT_BOOL(), \
|
||||||
NO_SB_OPT, RATELIMIT_ERRORS, \
|
NO_SB_OPT, RATELIMIT_ERRORS_DEFAULT, \
|
||||||
NULL, "Ratelimit error messages during fsck") \
|
NULL, "Ratelimit error messages during fsck") \
|
||||||
x(nochanges, u8, \
|
x(nochanges, u8, \
|
||||||
OPT_FS|OPT_MOUNT, \
|
OPT_FS|OPT_MOUNT, \
|
||||||
|
@ -1238,7 +1238,7 @@ use_clean:
|
|||||||
*/
|
*/
|
||||||
bch_verbose(c, "writing allocation info");
|
bch_verbose(c, "writing allocation info");
|
||||||
err = "error writing out alloc info";
|
err = "error writing out alloc info";
|
||||||
ret = bch2_alloc_write(c, BTREE_INSERT_LAZY_RW);
|
ret = bch2_alloc_write_all(c, BTREE_INSERT_LAZY_RW);
|
||||||
if (ret) {
|
if (ret) {
|
||||||
bch_err(c, "error writing alloc info");
|
bch_err(c, "error writing alloc info");
|
||||||
goto err;
|
goto err;
|
||||||
|
@ -722,10 +722,10 @@ static struct bch_fs *bch2_fs_alloc(struct bch_sb *sb, struct bch_opts opts)
|
|||||||
c->rebalance.enabled = 1;
|
c->rebalance.enabled = 1;
|
||||||
c->promote_whole_extents = true;
|
c->promote_whole_extents = true;
|
||||||
|
|
||||||
c->journal.write_time = &c->times[BCH_TIME_journal_write];
|
c->journal.flush_write_time = &c->times[BCH_TIME_journal_flush_write];
|
||||||
c->journal.delay_time = &c->times[BCH_TIME_journal_delay];
|
c->journal.noflush_write_time = &c->times[BCH_TIME_journal_noflush_write];
|
||||||
c->journal.blocked_time = &c->times[BCH_TIME_blocked_journal];
|
c->journal.blocked_time = &c->times[BCH_TIME_blocked_journal];
|
||||||
c->journal.flush_seq_time = &c->times[BCH_TIME_journal_flush_seq];
|
c->journal.flush_seq_time = &c->times[BCH_TIME_journal_flush_seq];
|
||||||
|
|
||||||
bch2_fs_btree_cache_init_early(&c->btree_cache);
|
bch2_fs_btree_cache_init_early(&c->btree_cache);
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user