1 // SPDX-License-Identifier: GPL-2.0
2
3 #include "bcachefs.h"
4 #include "bcachefs_ioctl.h"
5 #include "btree_cache.h"
6 #include "btree_journal_iter.h"
7 #include "btree_update.h"
8 #include "btree_write_buffer.h"
9 #include "buckets.h"
10 #include "compress.h"
11 #include "disk_accounting.h"
12 #include "error.h"
13 #include "journal_io.h"
14 #include "replicas.h"
15
16 /*
17 * Notes on disk accounting:
18 *
19 * We have two parallel sets of counters to be concerned with, and both must be
20 * kept in sync.
21 *
22 * - Persistent/on disk accounting, stored in the accounting btree and updated
23 * via btree write buffer updates that treat new accounting keys as deltas to
24 * apply to existing values. But reading from a write buffer btree is
25 * expensive, so we also have
26 *
27 * - In memory accounting, where accounting is stored as an array of percpu
28 * counters, indexed by an eytzinger array of disk acounting keys/bpos (which
29 * are the same thing, excepting byte swabbing on big endian).
30 *
31 * Cheap to read, but non persistent.
32 *
33 * Disk accounting updates are generated by transactional triggers; these run as
34 * keys enter and leave the btree, and can compare old and new versions of keys;
35 * the output of these triggers are deltas to the various counters.
36 *
37 * Disk accounting updates are done as btree write buffer updates, where the
38 * counters in the disk accounting key are deltas that will be applied to the
39 * counter in the btree when the key is flushed by the write buffer (or journal
40 * replay).
41 *
42 * To do a disk accounting update:
43 * - initialize a disk_accounting_pos, to specify which counter is being update
44 * - initialize counter deltas, as an array of 1-3 s64s
45 * - call bch2_disk_accounting_mod()
46 *
47 * This queues up the accounting update to be done at transaction commit time.
48 * Underneath, it's a normal btree write buffer update.
49 *
50 * The transaction commit path is responsible for propagating updates to the in
51 * memory counters, with bch2_accounting_mem_mod().
52 *
53 * The commit path also assigns every disk accounting update a unique version
54 * number, based on the journal sequence number and offset within that journal
55 * buffer; this is used by journal replay to determine which updates have been
56 * done.
57 *
58 * The transaction commit path also ensures that replicas entry accounting
59 * updates are properly marked in the superblock (so that we know whether we can
60 * mount without data being unavailable); it will update the superblock if
61 * bch2_accounting_mem_mod() tells it to.
62 */
63
64 static const char * const disk_accounting_type_strs[] = {
65 #define x(t, n, ...) [n] = #t,
66 BCH_DISK_ACCOUNTING_TYPES()
67 #undef x
68 NULL
69 };
70
accounting_key_init(struct bkey_i * k,struct disk_accounting_pos * pos,s64 * d,unsigned nr)71 static inline void accounting_key_init(struct bkey_i *k, struct disk_accounting_pos *pos,
72 s64 *d, unsigned nr)
73 {
74 struct bkey_i_accounting *acc = bkey_accounting_init(k);
75
76 acc->k.p = disk_accounting_pos_to_bpos(pos);
77 set_bkey_val_u64s(&acc->k, sizeof(struct bch_accounting) / sizeof(u64) + nr);
78
79 memcpy_u64s_small(acc->v.d, d, nr);
80 }
81
bch2_disk_accounting_mod(struct btree_trans * trans,struct disk_accounting_pos * k,s64 * d,unsigned nr,bool gc)82 int bch2_disk_accounting_mod(struct btree_trans *trans,
83 struct disk_accounting_pos *k,
84 s64 *d, unsigned nr, bool gc)
85 {
86 /* Normalize: */
87 switch (k->type) {
88 case BCH_DISK_ACCOUNTING_replicas:
89 bubble_sort(k->replicas.devs, k->replicas.nr_devs, u8_cmp);
90 break;
91 }
92
93 BUG_ON(nr > BCH_ACCOUNTING_MAX_COUNTERS);
94
95 struct { __BKEY_PADDED(k, BCH_ACCOUNTING_MAX_COUNTERS); } k_i;
96
97 accounting_key_init(&k_i.k, k, d, nr);
98
99 return likely(!gc)
100 ? bch2_trans_update_buffered(trans, BTREE_ID_accounting, &k_i.k)
101 : bch2_accounting_mem_add(trans, bkey_i_to_s_c_accounting(&k_i.k), true);
102 }
103
bch2_mod_dev_cached_sectors(struct btree_trans * trans,unsigned dev,s64 sectors,bool gc)104 int bch2_mod_dev_cached_sectors(struct btree_trans *trans,
105 unsigned dev, s64 sectors,
106 bool gc)
107 {
108 struct disk_accounting_pos acc = {
109 .type = BCH_DISK_ACCOUNTING_replicas,
110 };
111
112 bch2_replicas_entry_cached(&acc.replicas, dev);
113
114 return bch2_disk_accounting_mod(trans, &acc, §ors, 1, gc);
115 }
116
is_zero(char * start,char * end)117 static inline bool is_zero(char *start, char *end)
118 {
119 BUG_ON(start > end);
120
121 for (; start < end; start++)
122 if (*start)
123 return false;
124 return true;
125 }
126
127 #define field_end(p, member) (((void *) (&p.member)) + sizeof(p.member))
128
bch2_accounting_validate(struct bch_fs * c,struct bkey_s_c k,enum bch_validate_flags flags)129 int bch2_accounting_validate(struct bch_fs *c, struct bkey_s_c k,
130 enum bch_validate_flags flags)
131 {
132 struct disk_accounting_pos acc_k;
133 bpos_to_disk_accounting_pos(&acc_k, k.k->p);
134 void *end = &acc_k + 1;
135 int ret = 0;
136
137 bkey_fsck_err_on(bversion_zero(k.k->bversion),
138 c, accounting_key_version_0,
139 "accounting key with version=0");
140
141 switch (acc_k.type) {
142 case BCH_DISK_ACCOUNTING_nr_inodes:
143 end = field_end(acc_k, nr_inodes);
144 break;
145 case BCH_DISK_ACCOUNTING_persistent_reserved:
146 end = field_end(acc_k, persistent_reserved);
147 break;
148 case BCH_DISK_ACCOUNTING_replicas:
149 bkey_fsck_err_on(!acc_k.replicas.nr_devs,
150 c, accounting_key_replicas_nr_devs_0,
151 "accounting key replicas entry with nr_devs=0");
152
153 bkey_fsck_err_on(acc_k.replicas.nr_required > acc_k.replicas.nr_devs ||
154 (acc_k.replicas.nr_required > 1 &&
155 acc_k.replicas.nr_required == acc_k.replicas.nr_devs),
156 c, accounting_key_replicas_nr_required_bad,
157 "accounting key replicas entry with bad nr_required");
158
159 for (unsigned i = 0; i + 1 < acc_k.replicas.nr_devs; i++)
160 bkey_fsck_err_on(acc_k.replicas.devs[i] >= acc_k.replicas.devs[i + 1],
161 c, accounting_key_replicas_devs_unsorted,
162 "accounting key replicas entry with unsorted devs");
163
164 end = (void *) &acc_k.replicas + replicas_entry_bytes(&acc_k.replicas);
165 break;
166 case BCH_DISK_ACCOUNTING_dev_data_type:
167 end = field_end(acc_k, dev_data_type);
168 break;
169 case BCH_DISK_ACCOUNTING_compression:
170 end = field_end(acc_k, compression);
171 break;
172 case BCH_DISK_ACCOUNTING_snapshot:
173 end = field_end(acc_k, snapshot);
174 break;
175 case BCH_DISK_ACCOUNTING_btree:
176 end = field_end(acc_k, btree);
177 break;
178 case BCH_DISK_ACCOUNTING_rebalance_work:
179 end = field_end(acc_k, rebalance_work);
180 break;
181 }
182
183 bkey_fsck_err_on(!is_zero(end, (void *) (&acc_k + 1)),
184 c, accounting_key_junk_at_end,
185 "junk at end of accounting key");
186 fsck_err:
187 return ret;
188 }
189
bch2_accounting_key_to_text(struct printbuf * out,struct disk_accounting_pos * k)190 void bch2_accounting_key_to_text(struct printbuf *out, struct disk_accounting_pos *k)
191 {
192 if (k->type >= BCH_DISK_ACCOUNTING_TYPE_NR) {
193 prt_printf(out, "unknown type %u", k->type);
194 return;
195 }
196
197 prt_str(out, disk_accounting_type_strs[k->type]);
198 prt_str(out, " ");
199
200 switch (k->type) {
201 case BCH_DISK_ACCOUNTING_nr_inodes:
202 break;
203 case BCH_DISK_ACCOUNTING_persistent_reserved:
204 prt_printf(out, "replicas=%u", k->persistent_reserved.nr_replicas);
205 break;
206 case BCH_DISK_ACCOUNTING_replicas:
207 bch2_replicas_entry_to_text(out, &k->replicas);
208 break;
209 case BCH_DISK_ACCOUNTING_dev_data_type:
210 prt_printf(out, "dev=%u data_type=", k->dev_data_type.dev);
211 bch2_prt_data_type(out, k->dev_data_type.data_type);
212 break;
213 case BCH_DISK_ACCOUNTING_compression:
214 bch2_prt_compression_type(out, k->compression.type);
215 break;
216 case BCH_DISK_ACCOUNTING_snapshot:
217 prt_printf(out, "id=%u", k->snapshot.id);
218 break;
219 case BCH_DISK_ACCOUNTING_btree:
220 prt_printf(out, "btree=%s", bch2_btree_id_str(k->btree.id));
221 break;
222 }
223 }
224
bch2_accounting_to_text(struct printbuf * out,struct bch_fs * c,struct bkey_s_c k)225 void bch2_accounting_to_text(struct printbuf *out, struct bch_fs *c, struct bkey_s_c k)
226 {
227 struct bkey_s_c_accounting acc = bkey_s_c_to_accounting(k);
228 struct disk_accounting_pos acc_k;
229 bpos_to_disk_accounting_pos(&acc_k, k.k->p);
230
231 bch2_accounting_key_to_text(out, &acc_k);
232
233 for (unsigned i = 0; i < bch2_accounting_counters(k.k); i++)
234 prt_printf(out, " %lli", acc.v->d[i]);
235 }
236
bch2_accounting_swab(struct bkey_s k)237 void bch2_accounting_swab(struct bkey_s k)
238 {
239 for (u64 *p = (u64 *) k.v;
240 p < (u64 *) bkey_val_end(k);
241 p++)
242 *p = swab64(*p);
243 }
244
__accounting_to_replicas(struct bch_replicas_entry_v1 * r,struct disk_accounting_pos acc)245 static inline void __accounting_to_replicas(struct bch_replicas_entry_v1 *r,
246 struct disk_accounting_pos acc)
247 {
248 unsafe_memcpy(r, &acc.replicas,
249 replicas_entry_bytes(&acc.replicas),
250 "variable length struct");
251 }
252
accounting_to_replicas(struct bch_replicas_entry_v1 * r,struct bpos p)253 static inline bool accounting_to_replicas(struct bch_replicas_entry_v1 *r, struct bpos p)
254 {
255 struct disk_accounting_pos acc_k;
256 bpos_to_disk_accounting_pos(&acc_k, p);
257
258 switch (acc_k.type) {
259 case BCH_DISK_ACCOUNTING_replicas:
260 __accounting_to_replicas(r, acc_k);
261 return true;
262 default:
263 return false;
264 }
265 }
266
bch2_accounting_update_sb_one(struct bch_fs * c,struct bpos p)267 static int bch2_accounting_update_sb_one(struct bch_fs *c, struct bpos p)
268 {
269 struct bch_replicas_padded r;
270 return accounting_to_replicas(&r.e, p)
271 ? bch2_mark_replicas(c, &r.e)
272 : 0;
273 }
274
275 /*
276 * Ensure accounting keys being updated are present in the superblock, when
277 * applicable (i.e. replicas updates)
278 */
bch2_accounting_update_sb(struct btree_trans * trans)279 int bch2_accounting_update_sb(struct btree_trans *trans)
280 {
281 for (struct jset_entry *i = trans->journal_entries;
282 i != (void *) ((u64 *) trans->journal_entries + trans->journal_entries_u64s);
283 i = vstruct_next(i))
284 if (jset_entry_is_key(i) && i->start->k.type == KEY_TYPE_accounting) {
285 int ret = bch2_accounting_update_sb_one(trans->c, i->start->k.p);
286 if (ret)
287 return ret;
288 }
289
290 return 0;
291 }
292
__bch2_accounting_mem_insert(struct bch_fs * c,struct bkey_s_c_accounting a)293 static int __bch2_accounting_mem_insert(struct bch_fs *c, struct bkey_s_c_accounting a)
294 {
295 struct bch_accounting_mem *acc = &c->accounting;
296
297 /* raced with another insert, already present: */
298 if (eytzinger0_find(acc->k.data, acc->k.nr, sizeof(acc->k.data[0]),
299 accounting_pos_cmp, &a.k->p) < acc->k.nr)
300 return 0;
301
302 struct accounting_mem_entry n = {
303 .pos = a.k->p,
304 .bversion = a.k->bversion,
305 .nr_counters = bch2_accounting_counters(a.k),
306 .v[0] = __alloc_percpu_gfp(n.nr_counters * sizeof(u64),
307 sizeof(u64), GFP_KERNEL),
308 };
309
310 if (!n.v[0])
311 goto err;
312
313 if (acc->gc_running) {
314 n.v[1] = __alloc_percpu_gfp(n.nr_counters * sizeof(u64),
315 sizeof(u64), GFP_KERNEL);
316 if (!n.v[1])
317 goto err;
318 }
319
320 if (darray_push(&acc->k, n))
321 goto err;
322
323 eytzinger0_sort(acc->k.data, acc->k.nr, sizeof(acc->k.data[0]),
324 accounting_pos_cmp, NULL);
325 return 0;
326 err:
327 free_percpu(n.v[1]);
328 free_percpu(n.v[0]);
329 return -BCH_ERR_ENOMEM_disk_accounting;
330 }
331
bch2_accounting_mem_insert(struct bch_fs * c,struct bkey_s_c_accounting a,enum bch_accounting_mode mode)332 int bch2_accounting_mem_insert(struct bch_fs *c, struct bkey_s_c_accounting a,
333 enum bch_accounting_mode mode)
334 {
335 struct bch_replicas_padded r;
336
337 if (mode != BCH_ACCOUNTING_read &&
338 accounting_to_replicas(&r.e, a.k->p) &&
339 !bch2_replicas_marked_locked(c, &r.e))
340 return -BCH_ERR_btree_insert_need_mark_replicas;
341
342 percpu_up_read(&c->mark_lock);
343 percpu_down_write(&c->mark_lock);
344 int ret = __bch2_accounting_mem_insert(c, a);
345 percpu_up_write(&c->mark_lock);
346 percpu_down_read(&c->mark_lock);
347 return ret;
348 }
349
accounting_mem_entry_is_zero(struct accounting_mem_entry * e)350 static bool accounting_mem_entry_is_zero(struct accounting_mem_entry *e)
351 {
352 for (unsigned i = 0; i < e->nr_counters; i++)
353 if (percpu_u64_get(e->v[0] + i) ||
354 (e->v[1] &&
355 percpu_u64_get(e->v[1] + i)))
356 return false;
357 return true;
358 }
359
bch2_accounting_mem_gc(struct bch_fs * c)360 void bch2_accounting_mem_gc(struct bch_fs *c)
361 {
362 struct bch_accounting_mem *acc = &c->accounting;
363
364 percpu_down_write(&c->mark_lock);
365 struct accounting_mem_entry *dst = acc->k.data;
366
367 darray_for_each(acc->k, src) {
368 if (accounting_mem_entry_is_zero(src)) {
369 free_percpu(src->v[0]);
370 free_percpu(src->v[1]);
371 } else {
372 *dst++ = *src;
373 }
374 }
375
376 acc->k.nr = dst - acc->k.data;
377 eytzinger0_sort(acc->k.data, acc->k.nr, sizeof(acc->k.data[0]),
378 accounting_pos_cmp, NULL);
379 percpu_up_write(&c->mark_lock);
380 }
381
382 /*
383 * Read out accounting keys for replicas entries, as an array of
384 * bch_replicas_usage entries.
385 *
386 * Note: this may be deprecated/removed at smoe point in the future and replaced
387 * with something more general, it exists to support the ioctl used by the
388 * 'bcachefs fs usage' command.
389 */
bch2_fs_replicas_usage_read(struct bch_fs * c,darray_char * usage)390 int bch2_fs_replicas_usage_read(struct bch_fs *c, darray_char *usage)
391 {
392 struct bch_accounting_mem *acc = &c->accounting;
393 int ret = 0;
394
395 darray_init(usage);
396
397 percpu_down_read(&c->mark_lock);
398 darray_for_each(acc->k, i) {
399 struct {
400 struct bch_replicas_usage r;
401 u8 pad[BCH_BKEY_PTRS_MAX];
402 } u;
403
404 if (!accounting_to_replicas(&u.r.r, i->pos))
405 continue;
406
407 u64 sectors;
408 bch2_accounting_mem_read_counters(acc, i - acc->k.data, §ors, 1, false);
409 u.r.sectors = sectors;
410
411 ret = darray_make_room(usage, replicas_usage_bytes(&u.r));
412 if (ret)
413 break;
414
415 memcpy(&darray_top(*usage), &u.r, replicas_usage_bytes(&u.r));
416 usage->nr += replicas_usage_bytes(&u.r);
417 }
418 percpu_up_read(&c->mark_lock);
419
420 if (ret)
421 darray_exit(usage);
422 return ret;
423 }
424
bch2_fs_accounting_read(struct bch_fs * c,darray_char * out_buf,unsigned accounting_types_mask)425 int bch2_fs_accounting_read(struct bch_fs *c, darray_char *out_buf, unsigned accounting_types_mask)
426 {
427
428 struct bch_accounting_mem *acc = &c->accounting;
429 int ret = 0;
430
431 darray_init(out_buf);
432
433 percpu_down_read(&c->mark_lock);
434 darray_for_each(acc->k, i) {
435 struct disk_accounting_pos a_p;
436 bpos_to_disk_accounting_pos(&a_p, i->pos);
437
438 if (!(accounting_types_mask & BIT(a_p.type)))
439 continue;
440
441 ret = darray_make_room(out_buf, sizeof(struct bkey_i_accounting) +
442 sizeof(u64) * i->nr_counters);
443 if (ret)
444 break;
445
446 struct bkey_i_accounting *a_out =
447 bkey_accounting_init((void *) &darray_top(*out_buf));
448 set_bkey_val_u64s(&a_out->k, i->nr_counters);
449 a_out->k.p = i->pos;
450 bch2_accounting_mem_read_counters(acc, i - acc->k.data,
451 a_out->v.d, i->nr_counters, false);
452
453 if (!bch2_accounting_key_is_zero(accounting_i_to_s_c(a_out)))
454 out_buf->nr += bkey_bytes(&a_out->k);
455 }
456
457 percpu_up_read(&c->mark_lock);
458
459 if (ret)
460 darray_exit(out_buf);
461 return ret;
462 }
463
bch2_fs_accounting_to_text(struct printbuf * out,struct bch_fs * c)464 void bch2_fs_accounting_to_text(struct printbuf *out, struct bch_fs *c)
465 {
466 struct bch_accounting_mem *acc = &c->accounting;
467
468 percpu_down_read(&c->mark_lock);
469 out->atomic++;
470
471 eytzinger0_for_each(i, acc->k.nr) {
472 struct disk_accounting_pos acc_k;
473 bpos_to_disk_accounting_pos(&acc_k, acc->k.data[i].pos);
474
475 bch2_accounting_key_to_text(out, &acc_k);
476
477 u64 v[BCH_ACCOUNTING_MAX_COUNTERS];
478 bch2_accounting_mem_read_counters(acc, i, v, ARRAY_SIZE(v), false);
479
480 prt_str(out, ":");
481 for (unsigned j = 0; j < acc->k.data[i].nr_counters; j++)
482 prt_printf(out, " %llu", v[j]);
483 prt_newline(out);
484 }
485
486 --out->atomic;
487 percpu_up_read(&c->mark_lock);
488 }
489
bch2_accounting_free_counters(struct bch_accounting_mem * acc,bool gc)490 static void bch2_accounting_free_counters(struct bch_accounting_mem *acc, bool gc)
491 {
492 darray_for_each(acc->k, e) {
493 free_percpu(e->v[gc]);
494 e->v[gc] = NULL;
495 }
496 }
497
bch2_gc_accounting_start(struct bch_fs * c)498 int bch2_gc_accounting_start(struct bch_fs *c)
499 {
500 struct bch_accounting_mem *acc = &c->accounting;
501 int ret = 0;
502
503 percpu_down_write(&c->mark_lock);
504 darray_for_each(acc->k, e) {
505 e->v[1] = __alloc_percpu_gfp(e->nr_counters * sizeof(u64),
506 sizeof(u64), GFP_KERNEL);
507 if (!e->v[1]) {
508 bch2_accounting_free_counters(acc, true);
509 ret = -BCH_ERR_ENOMEM_disk_accounting;
510 break;
511 }
512 }
513
514 acc->gc_running = !ret;
515 percpu_up_write(&c->mark_lock);
516
517 return ret;
518 }
519
bch2_gc_accounting_done(struct bch_fs * c)520 int bch2_gc_accounting_done(struct bch_fs *c)
521 {
522 struct bch_accounting_mem *acc = &c->accounting;
523 struct btree_trans *trans = bch2_trans_get(c);
524 struct printbuf buf = PRINTBUF;
525 struct bpos pos = POS_MIN;
526 int ret = 0;
527
528 percpu_down_write(&c->mark_lock);
529 while (1) {
530 unsigned idx = eytzinger0_find_ge(acc->k.data, acc->k.nr, sizeof(acc->k.data[0]),
531 accounting_pos_cmp, &pos);
532
533 if (idx >= acc->k.nr)
534 break;
535
536 struct accounting_mem_entry *e = acc->k.data + idx;
537 pos = bpos_successor(e->pos);
538
539 struct disk_accounting_pos acc_k;
540 bpos_to_disk_accounting_pos(&acc_k, e->pos);
541
542 if (acc_k.type >= BCH_DISK_ACCOUNTING_TYPE_NR)
543 continue;
544
545 u64 src_v[BCH_ACCOUNTING_MAX_COUNTERS];
546 u64 dst_v[BCH_ACCOUNTING_MAX_COUNTERS];
547
548 unsigned nr = e->nr_counters;
549 bch2_accounting_mem_read_counters(acc, idx, dst_v, nr, false);
550 bch2_accounting_mem_read_counters(acc, idx, src_v, nr, true);
551
552 if (memcmp(dst_v, src_v, nr * sizeof(u64))) {
553 printbuf_reset(&buf);
554 prt_str(&buf, "accounting mismatch for ");
555 bch2_accounting_key_to_text(&buf, &acc_k);
556
557 prt_str(&buf, ": got");
558 for (unsigned j = 0; j < nr; j++)
559 prt_printf(&buf, " %llu", dst_v[j]);
560
561 prt_str(&buf, " should be");
562 for (unsigned j = 0; j < nr; j++)
563 prt_printf(&buf, " %llu", src_v[j]);
564
565 for (unsigned j = 0; j < nr; j++)
566 src_v[j] -= dst_v[j];
567
568 if (fsck_err(trans, accounting_mismatch, "%s", buf.buf)) {
569 percpu_up_write(&c->mark_lock);
570 ret = commit_do(trans, NULL, NULL, 0,
571 bch2_disk_accounting_mod(trans, &acc_k, src_v, nr, false));
572 percpu_down_write(&c->mark_lock);
573 if (ret)
574 goto err;
575
576 if (!test_bit(BCH_FS_may_go_rw, &c->flags)) {
577 memset(&trans->fs_usage_delta, 0, sizeof(trans->fs_usage_delta));
578 struct { __BKEY_PADDED(k, BCH_ACCOUNTING_MAX_COUNTERS); } k_i;
579
580 accounting_key_init(&k_i.k, &acc_k, src_v, nr);
581 bch2_accounting_mem_mod_locked(trans,
582 bkey_i_to_s_c_accounting(&k_i.k),
583 BCH_ACCOUNTING_normal);
584
585 preempt_disable();
586 struct bch_fs_usage_base *dst = this_cpu_ptr(c->usage);
587 struct bch_fs_usage_base *src = &trans->fs_usage_delta;
588 acc_u64s((u64 *) dst, (u64 *) src, sizeof(*src) / sizeof(u64));
589 preempt_enable();
590 }
591 }
592 }
593 }
594 err:
595 fsck_err:
596 percpu_up_write(&c->mark_lock);
597 printbuf_exit(&buf);
598 bch2_trans_put(trans);
599 bch_err_fn(c, ret);
600 return ret;
601 }
602
accounting_read_key(struct btree_trans * trans,struct bkey_s_c k)603 static int accounting_read_key(struct btree_trans *trans, struct bkey_s_c k)
604 {
605 struct bch_fs *c = trans->c;
606
607 if (k.k->type != KEY_TYPE_accounting)
608 return 0;
609
610 percpu_down_read(&c->mark_lock);
611 int ret = bch2_accounting_mem_mod_locked(trans, bkey_s_c_to_accounting(k),
612 BCH_ACCOUNTING_read);
613 percpu_up_read(&c->mark_lock);
614 return ret;
615 }
616
bch2_disk_accounting_validate_late(struct btree_trans * trans,struct disk_accounting_pos acc,u64 * v,unsigned nr)617 static int bch2_disk_accounting_validate_late(struct btree_trans *trans,
618 struct disk_accounting_pos acc,
619 u64 *v, unsigned nr)
620 {
621 struct bch_fs *c = trans->c;
622 struct printbuf buf = PRINTBUF;
623 int ret = 0, invalid_dev = -1;
624
625 switch (acc.type) {
626 case BCH_DISK_ACCOUNTING_replicas: {
627 struct bch_replicas_padded r;
628 __accounting_to_replicas(&r.e, acc);
629
630 for (unsigned i = 0; i < r.e.nr_devs; i++)
631 if (r.e.devs[i] != BCH_SB_MEMBER_INVALID &&
632 !bch2_dev_exists(c, r.e.devs[i])) {
633 invalid_dev = r.e.devs[i];
634 goto invalid_device;
635 }
636
637 /*
638 * All replicas entry checks except for invalid device are done
639 * in bch2_accounting_validate
640 */
641 BUG_ON(bch2_replicas_entry_validate(&r.e, c, &buf));
642
643 if (fsck_err_on(!bch2_replicas_marked_locked(c, &r.e),
644 trans, accounting_replicas_not_marked,
645 "accounting not marked in superblock replicas\n %s",
646 (printbuf_reset(&buf),
647 bch2_accounting_key_to_text(&buf, &acc),
648 buf.buf))) {
649 /*
650 * We're not RW yet and still single threaded, dropping
651 * and retaking lock is ok:
652 */
653 percpu_up_write(&c->mark_lock);
654 ret = bch2_mark_replicas(c, &r.e);
655 if (ret)
656 goto fsck_err;
657 percpu_down_write(&c->mark_lock);
658 }
659 break;
660 }
661
662 case BCH_DISK_ACCOUNTING_dev_data_type:
663 if (!bch2_dev_exists(c, acc.dev_data_type.dev)) {
664 invalid_dev = acc.dev_data_type.dev;
665 goto invalid_device;
666 }
667 break;
668 }
669
670 fsck_err:
671 printbuf_exit(&buf);
672 return ret;
673 invalid_device:
674 if (fsck_err(trans, accounting_to_invalid_device,
675 "accounting entry points to invalid device %i\n %s",
676 invalid_dev,
677 (printbuf_reset(&buf),
678 bch2_accounting_key_to_text(&buf, &acc),
679 buf.buf))) {
680 for (unsigned i = 0; i < nr; i++)
681 v[i] = -v[i];
682
683 ret = commit_do(trans, NULL, NULL, 0,
684 bch2_disk_accounting_mod(trans, &acc, v, nr, false)) ?:
685 -BCH_ERR_remove_disk_accounting_entry;
686 } else {
687 ret = -BCH_ERR_remove_disk_accounting_entry;
688 }
689 goto fsck_err;
690 }
691
692 /*
693 * At startup time, initialize the in memory accounting from the btree (and
694 * journal)
695 */
bch2_accounting_read(struct bch_fs * c)696 int bch2_accounting_read(struct bch_fs *c)
697 {
698 struct bch_accounting_mem *acc = &c->accounting;
699 struct btree_trans *trans = bch2_trans_get(c);
700 struct printbuf buf = PRINTBUF;
701
702 int ret = for_each_btree_key(trans, iter,
703 BTREE_ID_accounting, POS_MIN,
704 BTREE_ITER_prefetch|BTREE_ITER_all_snapshots, k, ({
705 struct bkey u;
706 struct bkey_s_c k = bch2_btree_path_peek_slot_exact(btree_iter_path(trans, &iter), &u);
707 accounting_read_key(trans, k);
708 }));
709 if (ret)
710 goto err;
711
712 struct journal_keys *keys = &c->journal_keys;
713 struct journal_key *dst = keys->data;
714 move_gap(keys, keys->nr);
715
716 darray_for_each(*keys, i) {
717 if (i->k->k.type == KEY_TYPE_accounting) {
718 struct bkey_s_c k = bkey_i_to_s_c(i->k);
719 unsigned idx = eytzinger0_find(acc->k.data, acc->k.nr,
720 sizeof(acc->k.data[0]),
721 accounting_pos_cmp, &k.k->p);
722
723 bool applied = idx < acc->k.nr &&
724 bversion_cmp(acc->k.data[idx].bversion, k.k->bversion) >= 0;
725
726 if (applied)
727 continue;
728
729 if (i + 1 < &darray_top(*keys) &&
730 i[1].k->k.type == KEY_TYPE_accounting &&
731 !journal_key_cmp(i, i + 1)) {
732 WARN_ON(bversion_cmp(i[0].k->k.bversion, i[1].k->k.bversion) >= 0);
733
734 i[1].journal_seq = i[0].journal_seq;
735
736 bch2_accounting_accumulate(bkey_i_to_accounting(i[1].k),
737 bkey_s_c_to_accounting(k));
738 continue;
739 }
740
741 ret = accounting_read_key(trans, k);
742 if (ret)
743 goto err;
744 }
745
746 *dst++ = *i;
747 }
748 keys->gap = keys->nr = dst - keys->data;
749
750 percpu_down_write(&c->mark_lock);
751 unsigned i = 0;
752 while (i < acc->k.nr) {
753 unsigned idx = inorder_to_eytzinger0(i, acc->k.nr);
754
755 struct disk_accounting_pos acc_k;
756 bpos_to_disk_accounting_pos(&acc_k, acc->k.data[idx].pos);
757
758 u64 v[BCH_ACCOUNTING_MAX_COUNTERS];
759 bch2_accounting_mem_read_counters(acc, idx, v, ARRAY_SIZE(v), false);
760
761 /*
762 * If the entry counters are zeroed, it should be treated as
763 * nonexistent - it might point to an invalid device.
764 *
765 * Remove it, so that if it's re-added it gets re-marked in the
766 * superblock:
767 */
768 ret = bch2_is_zero(v, sizeof(v[0]) * acc->k.data[idx].nr_counters)
769 ? -BCH_ERR_remove_disk_accounting_entry
770 : bch2_disk_accounting_validate_late(trans, acc_k,
771 v, acc->k.data[idx].nr_counters);
772
773 if (ret == -BCH_ERR_remove_disk_accounting_entry) {
774 free_percpu(acc->k.data[idx].v[0]);
775 free_percpu(acc->k.data[idx].v[1]);
776 darray_remove_item(&acc->k, &acc->k.data[idx]);
777 eytzinger0_sort(acc->k.data, acc->k.nr, sizeof(acc->k.data[0]),
778 accounting_pos_cmp, NULL);
779 ret = 0;
780 continue;
781 }
782
783 if (ret)
784 goto fsck_err;
785 i++;
786 }
787
788 preempt_disable();
789 struct bch_fs_usage_base *usage = this_cpu_ptr(c->usage);
790
791 for (unsigned i = 0; i < acc->k.nr; i++) {
792 struct disk_accounting_pos k;
793 bpos_to_disk_accounting_pos(&k, acc->k.data[i].pos);
794
795 u64 v[BCH_ACCOUNTING_MAX_COUNTERS];
796 bch2_accounting_mem_read_counters(acc, i, v, ARRAY_SIZE(v), false);
797
798 switch (k.type) {
799 case BCH_DISK_ACCOUNTING_persistent_reserved:
800 usage->reserved += v[0] * k.persistent_reserved.nr_replicas;
801 break;
802 case BCH_DISK_ACCOUNTING_replicas:
803 fs_usage_data_type_to_base(usage, k.replicas.data_type, v[0]);
804 break;
805 case BCH_DISK_ACCOUNTING_dev_data_type:
806 rcu_read_lock();
807 struct bch_dev *ca = bch2_dev_rcu(c, k.dev_data_type.dev);
808 if (ca) {
809 struct bch_dev_usage_type __percpu *d = &ca->usage->d[k.dev_data_type.data_type];
810 percpu_u64_set(&d->buckets, v[0]);
811 percpu_u64_set(&d->sectors, v[1]);
812 percpu_u64_set(&d->fragmented, v[2]);
813
814 if (k.dev_data_type.data_type == BCH_DATA_sb ||
815 k.dev_data_type.data_type == BCH_DATA_journal)
816 usage->hidden += v[0] * ca->mi.bucket_size;
817 }
818 rcu_read_unlock();
819 break;
820 }
821 }
822 preempt_enable();
823 fsck_err:
824 percpu_up_write(&c->mark_lock);
825 err:
826 printbuf_exit(&buf);
827 bch2_trans_put(trans);
828 bch_err_fn(c, ret);
829 return ret;
830 }
831
bch2_dev_usage_remove(struct bch_fs * c,unsigned dev)832 int bch2_dev_usage_remove(struct bch_fs *c, unsigned dev)
833 {
834 return bch2_trans_run(c,
835 bch2_btree_write_buffer_flush_sync(trans) ?:
836 for_each_btree_key_commit(trans, iter, BTREE_ID_accounting, POS_MIN,
837 BTREE_ITER_all_snapshots, k, NULL, NULL, 0, ({
838 struct disk_accounting_pos acc;
839 bpos_to_disk_accounting_pos(&acc, k.k->p);
840
841 acc.type == BCH_DISK_ACCOUNTING_dev_data_type &&
842 acc.dev_data_type.dev == dev
843 ? bch2_btree_bit_mod_buffered(trans, BTREE_ID_accounting, k.k->p, 0)
844 : 0;
845 })) ?:
846 bch2_btree_write_buffer_flush_sync(trans));
847 }
848
bch2_dev_usage_init(struct bch_dev * ca,bool gc)849 int bch2_dev_usage_init(struct bch_dev *ca, bool gc)
850 {
851 struct bch_fs *c = ca->fs;
852 struct disk_accounting_pos acc = {
853 .type = BCH_DISK_ACCOUNTING_dev_data_type,
854 .dev_data_type.dev = ca->dev_idx,
855 .dev_data_type.data_type = BCH_DATA_free,
856 };
857 u64 v[3] = { ca->mi.nbuckets - ca->mi.first_bucket, 0, 0 };
858
859 int ret = bch2_trans_do(c, ({
860 bch2_disk_accounting_mod(trans, &acc, v, ARRAY_SIZE(v), gc) ?:
861 (!gc ? bch2_trans_commit(trans, NULL, NULL, 0) : 0);
862 }));
863 bch_err_fn(c, ret);
864 return ret;
865 }
866
bch2_verify_accounting_clean(struct bch_fs * c)867 void bch2_verify_accounting_clean(struct bch_fs *c)
868 {
869 bool mismatch = false;
870 struct bch_fs_usage_base base = {}, base_inmem = {};
871
872 bch2_trans_run(c,
873 for_each_btree_key(trans, iter,
874 BTREE_ID_accounting, POS_MIN,
875 BTREE_ITER_all_snapshots, k, ({
876 u64 v[BCH_ACCOUNTING_MAX_COUNTERS];
877 struct bkey_s_c_accounting a = bkey_s_c_to_accounting(k);
878 unsigned nr = bch2_accounting_counters(k.k);
879
880 struct disk_accounting_pos acc_k;
881 bpos_to_disk_accounting_pos(&acc_k, k.k->p);
882
883 if (acc_k.type >= BCH_DISK_ACCOUNTING_TYPE_NR)
884 continue;
885
886 if (acc_k.type == BCH_DISK_ACCOUNTING_inum)
887 continue;
888
889 bch2_accounting_mem_read(c, k.k->p, v, nr);
890
891 if (memcmp(a.v->d, v, nr * sizeof(u64))) {
892 struct printbuf buf = PRINTBUF;
893
894 bch2_bkey_val_to_text(&buf, c, k);
895 prt_str(&buf, " !=");
896 for (unsigned j = 0; j < nr; j++)
897 prt_printf(&buf, " %llu", v[j]);
898
899 pr_err("%s", buf.buf);
900 printbuf_exit(&buf);
901 mismatch = true;
902 }
903
904 switch (acc_k.type) {
905 case BCH_DISK_ACCOUNTING_persistent_reserved:
906 base.reserved += acc_k.persistent_reserved.nr_replicas * a.v->d[0];
907 break;
908 case BCH_DISK_ACCOUNTING_replicas:
909 fs_usage_data_type_to_base(&base, acc_k.replicas.data_type, a.v->d[0]);
910 break;
911 case BCH_DISK_ACCOUNTING_dev_data_type: {
912 rcu_read_lock();
913 struct bch_dev *ca = bch2_dev_rcu(c, acc_k.dev_data_type.dev);
914 if (!ca) {
915 rcu_read_unlock();
916 continue;
917 }
918
919 v[0] = percpu_u64_get(&ca->usage->d[acc_k.dev_data_type.data_type].buckets);
920 v[1] = percpu_u64_get(&ca->usage->d[acc_k.dev_data_type.data_type].sectors);
921 v[2] = percpu_u64_get(&ca->usage->d[acc_k.dev_data_type.data_type].fragmented);
922 rcu_read_unlock();
923
924 if (memcmp(a.v->d, v, 3 * sizeof(u64))) {
925 struct printbuf buf = PRINTBUF;
926
927 bch2_bkey_val_to_text(&buf, c, k);
928 prt_str(&buf, " in mem");
929 for (unsigned j = 0; j < nr; j++)
930 prt_printf(&buf, " %llu", v[j]);
931
932 pr_err("dev accounting mismatch: %s", buf.buf);
933 printbuf_exit(&buf);
934 mismatch = true;
935 }
936 }
937 }
938
939 0;
940 })));
941
942 acc_u64s_percpu(&base_inmem.hidden, &c->usage->hidden, sizeof(base_inmem) / sizeof(u64));
943
944 #define check(x) \
945 if (base.x != base_inmem.x) { \
946 pr_err("fs_usage_base.%s mismatch: %llu != %llu", #x, base.x, base_inmem.x); \
947 mismatch = true; \
948 }
949
950 //check(hidden);
951 check(btree);
952 check(data);
953 check(cached);
954 check(reserved);
955 check(nr_inodes);
956
957 WARN_ON(mismatch);
958 }
959
bch2_accounting_gc_free(struct bch_fs * c)960 void bch2_accounting_gc_free(struct bch_fs *c)
961 {
962 lockdep_assert_held(&c->mark_lock);
963
964 struct bch_accounting_mem *acc = &c->accounting;
965
966 bch2_accounting_free_counters(acc, true);
967 acc->gc_running = false;
968 }
969
bch2_fs_accounting_exit(struct bch_fs * c)970 void bch2_fs_accounting_exit(struct bch_fs *c)
971 {
972 struct bch_accounting_mem *acc = &c->accounting;
973
974 bch2_accounting_free_counters(acc, false);
975 darray_exit(&acc->k);
976 }
977