diff options
author | Kent Overstreet <kent.overstreet@gmail.com> | 2017-03-04 23:09:27 -0900 |
---|---|---|
committer | Kent Overstreet <kent.overstreet@gmail.com> | 2017-03-17 19:49:18 -0800 |
commit | 6edd6d764dfb7bf2e41cd9a9b8df1f7a38c0438c (patch) | |
tree | c977ca018bacbb8caf5d6d888e0d6f4e7ad42998 | |
parent | f81b41a1750e73a52c6f0071a451141e73f3f395 (diff) |
bcachefs: bch_sb_field refactoring
-rw-r--r-- | fs/bcachefs/bcachefs_format.h | 2 | ||||
-rw-r--r-- | fs/bcachefs/checksum.c | 5 | ||||
-rw-r--r-- | fs/bcachefs/journal.c | 13 | ||||
-rw-r--r-- | fs/bcachefs/super-io.c | 43 | ||||
-rw-r--r-- | fs/bcachefs/super-io.h | 44 | ||||
-rw-r--r-- | fs/bcachefs/super.c | 12 |
6 files changed, 63 insertions, 56 deletions
diff --git a/fs/bcachefs/bcachefs_format.h b/fs/bcachefs/bcachefs_format.h index dbb02742c47b..d70e2e32449e 100644 --- a/fs/bcachefs/bcachefs_format.h +++ b/fs/bcachefs/bcachefs_format.h @@ -821,7 +821,7 @@ struct bch_sb_field { __le32 type; }; -enum bch_sb_field_types { +enum bch_sb_field_type { BCH_SB_FIELD_journal = 0, BCH_SB_FIELD_members = 1, BCH_SB_FIELD_crypt = 2, diff --git a/fs/bcachefs/checksum.c b/fs/bcachefs/checksum.c index dae52d497b1a..004cc8292749 100644 --- a/fs/bcachefs/checksum.c +++ b/fs/bcachefs/checksum.c @@ -539,15 +539,12 @@ int bch_enable_encryption(struct cache_set *c, bool keyed) if (ret) goto err; - crypt = container_of_or_null(bch_fs_sb_field_resize(c, NULL, - sizeof(*crypt) / sizeof(u64)), - struct bch_sb_field_crypt, field); + crypt = bch_fs_sb_resize_crypt(c, sizeof(*crypt) / sizeof(u64)); if (!crypt) { ret = -ENOMEM; /* XXX this technically could be -ENOSPC */ goto err; } - crypt->field.type = BCH_SB_FIELD_crypt; crypt->key = key; /* write superblock */ diff --git a/fs/bcachefs/journal.c b/fs/bcachefs/journal.c index 72505e5b45fb..de2f155be6aa 100644 --- a/fs/bcachefs/journal.c +++ b/fs/bcachefs/journal.c @@ -545,8 +545,7 @@ static int journal_entry_validate(struct cache_set *c, return BCH_FSCK_UNKNOWN_VERSION; } - if (mustfix_fsck_err_on(bytes > bucket_sectors_left << 9 || - bytes > c->journal.entry_size_max, c, + if (mustfix_fsck_err_on(bytes > bucket_sectors_left << 9, c, "journal entry too big (%zu bytes), sector %lluu", bytes, sector)) { /* XXX: note we might have missing journal entries */ @@ -1540,7 +1539,6 @@ static int bch_set_nr_journal_buckets(struct cache_set *c, struct cache *ca, struct journal *j = &c->journal; struct journal_device *ja = &ca->journal; struct bch_sb_field_journal *journal_buckets; - struct bch_sb_field *f; struct disk_reservation disk_res = { 0, 0 }; struct closure cl; u64 *new_bucket_seq = NULL, *new_buckets = NULL; @@ -1572,13 +1570,10 @@ static int bch_set_nr_journal_buckets(struct cache_set *c, struct cache *ca, if (!new_buckets || !new_bucket_seq) goto err; - journal_buckets = bch_sb_get_journal(ca->disk_sb.sb); - f = bch_dev_sb_field_resize(&ca->disk_sb, &journal_buckets->field, nr + - sizeof(*journal_buckets) / sizeof(u64)); - if (!f) + journal_buckets = bch_sb_resize_journal(&ca->disk_sb, + nr + sizeof(*journal_buckets) / sizeof(u64)); + if (!journal_buckets) goto err; - f->type = BCH_SB_FIELD_journal; - journal_buckets = container_of(f, struct bch_sb_field_journal, field); spin_lock(&j->lock); memcpy(new_buckets, ja->buckets, ja->nr * sizeof(u64)); diff --git a/fs/bcachefs/super-io.c b/fs/bcachefs/super-io.c index 6c3fc703a772..f316f176e20d 100644 --- a/fs/bcachefs/super-io.c +++ b/fs/bcachefs/super-io.c @@ -18,7 +18,7 @@ static inline void __bch_sb_layout_size_assert(void) } struct bch_sb_field *bch_sb_field_get(struct bch_sb *sb, - enum bch_sb_field_types type) + enum bch_sb_field_type type) { struct bch_sb_field *f; @@ -75,7 +75,7 @@ static int __bch_super_realloc(struct bcache_superblock *sb, unsigned order) return 0; } -int bch_dev_sb_realloc(struct bcache_superblock *sb, unsigned u64s) +static int bch_sb_realloc(struct bcache_superblock *sb, unsigned u64s) { u64 new_bytes = __vstruct_bytes(struct bch_sb, u64s); u64 max_bytes = 512 << sb->sb->layout.sb_max_size_bits; @@ -141,13 +141,29 @@ static struct bch_sb_field *__bch_sb_field_resize(struct bch_sb *sb, le32_add_cpu(&sb->u64s, u64s - old_u64s); return f; +} + +struct bch_sb_field *bch_sb_field_resize(struct bcache_superblock *sb, + enum bch_sb_field_type type, + unsigned u64s) +{ + struct bch_sb_field *f = bch_sb_field_get(sb->sb, type); + ssize_t old_u64s = f ? le32_to_cpu(f->u64s) : 0; + ssize_t d = -old_u64s + u64s; + if (bch_sb_realloc(sb, le32_to_cpu(sb->sb->u64s) + d)) + return NULL; + + f = __bch_sb_field_resize(sb->sb, f, u64s); + f->type = type; + return f; } struct bch_sb_field *bch_fs_sb_field_resize(struct cache_set *c, - struct bch_sb_field *f, + enum bch_sb_field_type type, unsigned u64s) { + struct bch_sb_field *f = bch_sb_field_get(c->disk_sb, type); ssize_t old_u64s = f ? le32_to_cpu(f->u64s) : 0; ssize_t d = -old_u64s + u64s; struct cache *ca; @@ -161,26 +177,15 @@ struct bch_sb_field *bch_fs_sb_field_resize(struct cache_set *c, for_each_cache(ca, c, i) { struct bcache_superblock *sb = &ca->disk_sb; - if (bch_dev_sb_realloc(sb, le32_to_cpu(sb->sb->u64s) + d)) { + if (bch_sb_realloc(sb, le32_to_cpu(sb->sb->u64s) + d)) { percpu_ref_put(&ca->ref); return NULL; } } - return __bch_sb_field_resize(c->disk_sb, f, u64s); -} - -struct bch_sb_field *bch_dev_sb_field_resize(struct bcache_superblock *sb, - struct bch_sb_field *f, - unsigned u64s) -{ - ssize_t old_u64s = f ? le32_to_cpu(f->u64s) : 0; - ssize_t d = -old_u64s + u64s; - - if (bch_dev_sb_realloc(sb, le32_to_cpu(sb->sb->u64s) + d)) - return NULL; - - return __bch_sb_field_resize(sb->sb, f, u64s); + f = __bch_sb_field_resize(c->disk_sb, f, u64s); + f->type = type; + return f; } static const char *validate_sb_layout(struct bch_sb_layout *layout) @@ -589,7 +594,7 @@ int bch_sb_from_cache_set(struct cache_set *c, struct cache *ca) unsigned u64s = le32_to_cpu(src->u64s) + journal_u64s; int ret; - ret = bch_dev_sb_realloc(&ca->disk_sb, u64s); + ret = bch_sb_realloc(&ca->disk_sb, u64s); if (ret) return ret; diff --git a/fs/bcachefs/super-io.h b/fs/bcachefs/super-io.h index c810aec193fb..ae1e8b9dc304 100644 --- a/fs/bcachefs/super-io.h +++ b/fs/bcachefs/super-io.h @@ -6,16 +6,35 @@ #include <asm/byteorder.h> -struct bch_sb_field *bch_sb_field_get(struct bch_sb *, enum bch_sb_field_types); - -#define BCH_SB_FIELD_TYPE(_name) \ -static inline struct bch_sb_field_##_name * \ -bch_sb_get_##_name(struct bch_sb *sb) \ -{ \ - struct bch_sb_field *f = \ - bch_sb_field_get(sb, BCH_SB_FIELD_##_name); \ - \ - return container_of_or_null(f, struct bch_sb_field_##_name, field);\ +struct bch_sb_field *bch_sb_field_get(struct bch_sb *, enum bch_sb_field_type); +struct bch_sb_field *bch_sb_field_resize(struct bcache_superblock *, + enum bch_sb_field_type, unsigned); +struct bch_sb_field *bch_fs_sb_field_resize(struct cache_set *, + enum bch_sb_field_type, unsigned); + +#define field_to_type(_f, _name) \ + container_of_or_null(_f, struct bch_sb_field_##_name, field) + +#define BCH_SB_FIELD_TYPE(_name) \ +static inline struct bch_sb_field_##_name * \ +bch_sb_get_##_name(struct bch_sb *sb) \ +{ \ + return field_to_type(bch_sb_field_get(sb, \ + BCH_SB_FIELD_##_name), _name); \ +} \ + \ +static inline struct bch_sb_field_##_name * \ +bch_sb_resize_##_name(struct bcache_superblock *sb, unsigned u64s) \ +{ \ + return field_to_type(bch_sb_field_resize(sb, \ + BCH_SB_FIELD_##_name, u64s), _name); \ +} \ + \ +static inline struct bch_sb_field_##_name * \ +bch_fs_sb_resize_##_name(struct cache_set *c, unsigned u64s) \ +{ \ + return field_to_type(bch_fs_sb_field_resize(c, \ + BCH_SB_FIELD_##_name, u64s), _name); \ } BCH_SB_FIELD_TYPE(journal); @@ -85,11 +104,6 @@ int bch_fs_mi_update(struct cache_set *, struct bch_member *, unsigned); int bch_sb_to_cache_set(struct cache_set *, struct bch_sb *); int bch_sb_from_cache_set(struct cache_set *, struct cache *); -struct bch_sb_field *bch_fs_sb_field_resize(struct cache_set *, - struct bch_sb_field *, unsigned); -struct bch_sb_field *bch_dev_sb_field_resize(struct bcache_superblock *, - struct bch_sb_field *, unsigned); - void bch_free_super(struct bcache_superblock *); int bch_super_realloc(struct bcache_superblock *, unsigned); diff --git a/fs/bcachefs/super.c b/fs/bcachefs/super.c index 9bb5f8e393ac..cc3731e3f368 100644 --- a/fs/bcachefs/super.c +++ b/fs/bcachefs/super.c @@ -1512,7 +1512,6 @@ int bch_dev_add(struct cache_set *c, const char *path) struct bcache_superblock sb; const char *err; struct cache *ca; - struct bch_sb_field *f; struct bch_sb_field_members *mi, *dev_mi; struct bch_member saved_mi; unsigned dev_idx, nr_devices, u64s; @@ -1571,17 +1570,14 @@ have_slot: sizeof(struct bch_member) * nr_devices) / sizeof(u64); err = "no space in superblock for member info"; - f = bch_fs_sb_field_resize(c, &mi->field, u64s); - if (!f) + mi = bch_fs_sb_resize_members(c, u64s); + if (!mi) goto err_unlock; - mi = container_of(f, struct bch_sb_field_members, field); - - f = bch_dev_sb_field_resize(&sb, &dev_mi->field, u64s); - if (!f) + dev_mi = bch_sb_resize_members(&sb, u64s); + if (!dev_mi) goto err_unlock; - dev_mi = container_of(f, struct bch_sb_field_members, field); memcpy(dev_mi, mi, u64s * sizeof(u64)); dev_mi->members[dev_idx] = saved_mi; |