diff options
author | Kent Overstreet <kent.overstreet@gmail.com> | 2020-12-15 12:53:30 -0500 |
---|---|---|
committer | Kent Overstreet <kent.overstreet@gmail.com> | 2020-12-17 14:08:26 -0500 |
commit | 369468267c93e7c7f4277aec398d5eee882b1b3b (patch) | |
tree | 632552f898134e7dd02e40cee88c082d3a5de04a | |
parent | 34881783a2bdfa44308d9e2d06b0d79b7453b547 (diff) |
bcachefs: Use separate new stripes for copygc and non-copygc
Allocations for copygc have to be kept separate from everything else,
so that copygc doesn't get starved.
Signed-off-by: Kent Overstreet <kent.overstreet@gmail.com>
-rw-r--r-- | fs/bcachefs/alloc_foreground.c | 4 | ||||
-rw-r--r-- | fs/bcachefs/alloc_types.h | 1 | ||||
-rw-r--r-- | fs/bcachefs/ec.c | 27 | ||||
-rw-r--r-- | fs/bcachefs/ec.h | 3 |
4 files changed, 23 insertions, 12 deletions
diff --git a/fs/bcachefs/alloc_foreground.c b/fs/bcachefs/alloc_foreground.c index 0c5c69d643f6..6d016592fbe1 100644 --- a/fs/bcachefs/alloc_foreground.c +++ b/fs/bcachefs/alloc_foreground.c @@ -486,7 +486,9 @@ bucket_alloc_from_stripe(struct bch_fs *c, if (ec_open_bucket(c, ptrs)) return 0; - h = bch2_ec_stripe_head_get(c, target, 0, nr_replicas - 1, cl); + h = bch2_ec_stripe_head_get(c, target, 0, nr_replicas - 1, + wp == &c->copygc_write_point, + cl); if (IS_ERR(h)) return -PTR_ERR(h); if (!h) diff --git a/fs/bcachefs/alloc_types.h b/fs/bcachefs/alloc_types.h index 20705460bb0a..61938ed64605 100644 --- a/fs/bcachefs/alloc_types.h +++ b/fs/bcachefs/alloc_types.h @@ -89,7 +89,6 @@ struct write_point { u64 last_used; unsigned long write_point; enum bch_data_type type; - bool is_ec; /* calculated based on how many pointers we're actually going to use: */ unsigned sectors_free; diff --git a/fs/bcachefs/ec.c b/fs/bcachefs/ec.c index 903b81744c8f..c0ff0e0120d1 100644 --- a/fs/bcachefs/ec.c +++ b/fs/bcachefs/ec.c @@ -1158,7 +1158,8 @@ static int ec_new_stripe_alloc(struct bch_fs *c, struct ec_stripe_head *h) static struct ec_stripe_head * ec_new_stripe_head_alloc(struct bch_fs *c, unsigned target, - unsigned algo, unsigned redundancy) + unsigned algo, unsigned redundancy, + bool copygc) { struct ec_stripe_head *h; struct bch_dev *ca; @@ -1174,6 +1175,7 @@ ec_new_stripe_head_alloc(struct bch_fs *c, unsigned target, h->target = target; h->algo = algo; h->redundancy = redundancy; + h->copygc = copygc; rcu_read_lock(); h->devs = target_rw_devs(c, BCH_DATA_user, target); @@ -1205,9 +1207,10 @@ void bch2_ec_stripe_head_put(struct bch_fs *c, struct ec_stripe_head *h) } struct ec_stripe_head *__bch2_ec_stripe_head_get(struct bch_fs *c, - unsigned target, - unsigned algo, - unsigned redundancy) + unsigned target, + unsigned algo, + unsigned redundancy, + bool copygc) { struct ec_stripe_head *h; @@ -1218,12 +1221,13 @@ struct ec_stripe_head *__bch2_ec_stripe_head_get(struct bch_fs *c, list_for_each_entry(h, &c->ec_stripe_head_list, list) if (h->target == target && h->algo == algo && - h->redundancy == redundancy) { + h->redundancy == redundancy && + h->copygc == copygc) { mutex_lock(&h->lock); goto found; } - h = ec_new_stripe_head_alloc(c, target, algo, redundancy); + h = ec_new_stripe_head_alloc(c, target, algo, redundancy, copygc); found: mutex_unlock(&c->ec_stripe_head_lock); return h; @@ -1268,7 +1272,9 @@ new_stripe_alloc_buckets(struct bch_fs *c, struct ec_stripe_head *h, h->redundancy, &nr_have, &have_cache, - RESERVE_NONE, + h->copygc + ? RESERVE_MOVINGGC + : RESERVE_NONE, 0, cl); if (ret) @@ -1284,7 +1290,9 @@ new_stripe_alloc_buckets(struct bch_fs *c, struct ec_stripe_head *h, nr_data, &nr_have, &have_cache, - RESERVE_NONE, + h->copygc + ? RESERVE_MOVINGGC + : RESERVE_NONE, 0, cl); if (ret) @@ -1353,6 +1361,7 @@ struct ec_stripe_head *bch2_ec_stripe_head_get(struct bch_fs *c, unsigned target, unsigned algo, unsigned redundancy, + bool copygc, struct closure *cl) { struct ec_stripe_head *h; @@ -1361,7 +1370,7 @@ struct ec_stripe_head *bch2_ec_stripe_head_get(struct bch_fs *c, s64 idx; int ret; - h = __bch2_ec_stripe_head_get(c, target, algo, redundancy); + h = __bch2_ec_stripe_head_get(c, target, algo, redundancy, copygc); if (!h) { bch_err(c, "no stripe head"); return NULL; diff --git a/fs/bcachefs/ec.h b/fs/bcachefs/ec.h index 3f1999bae6d4..97a263cf9c87 100644 --- a/fs/bcachefs/ec.h +++ b/fs/bcachefs/ec.h @@ -122,6 +122,7 @@ struct ec_stripe_head { unsigned target; unsigned algo; unsigned redundancy; + bool copygc; struct bch_devs_mask devs; unsigned nr_active_devs; @@ -147,7 +148,7 @@ int bch2_ec_stripe_new_alloc(struct bch_fs *, struct ec_stripe_head *); void bch2_ec_stripe_head_put(struct bch_fs *, struct ec_stripe_head *); struct ec_stripe_head *bch2_ec_stripe_head_get(struct bch_fs *, - unsigned, unsigned, unsigned, struct closure *); + unsigned, unsigned, unsigned, bool, struct closure *); void bch2_stripes_heap_update(struct bch_fs *, struct stripe *, size_t); void bch2_stripes_heap_del(struct bch_fs *, struct stripe *, size_t); |