xref: /linux/fs/bcachefs/extents.h (revision 2573c25e2c482b53b6e1142ff3cd28f6de13e659)
1 /* SPDX-License-Identifier: GPL-2.0 */
2 #ifndef _BCACHEFS_EXTENTS_H
3 #define _BCACHEFS_EXTENTS_H
4 
5 #include "bcachefs.h"
6 #include "bkey.h"
7 #include "extents_types.h"
8 
9 struct bch_fs;
10 struct btree_trans;
11 enum bkey_invalid_flags;
12 
13 /* extent entries: */
14 
15 #define extent_entry_last(_e)						\
16 	((typeof(&(_e).v->start[0])) bkey_val_end(_e))
17 
18 #define entry_to_ptr(_entry)						\
19 ({									\
20 	EBUG_ON((_entry) && !extent_entry_is_ptr(_entry));		\
21 									\
22 	__builtin_choose_expr(						\
23 		type_is_exact(_entry, const union bch_extent_entry *),	\
24 		(const struct bch_extent_ptr *) (_entry),		\
25 		(struct bch_extent_ptr *) (_entry));			\
26 })
27 
28 /* downcast, preserves const */
29 #define to_entry(_entry)						\
30 ({									\
31 	BUILD_BUG_ON(!type_is(_entry, union bch_extent_crc *) &&	\
32 		     !type_is(_entry, struct bch_extent_ptr *) &&	\
33 		     !type_is(_entry, struct bch_extent_stripe_ptr *));	\
34 									\
35 	__builtin_choose_expr(						\
36 		(type_is_exact(_entry, const union bch_extent_crc *) ||	\
37 		 type_is_exact(_entry, const struct bch_extent_ptr *) ||\
38 		 type_is_exact(_entry, const struct bch_extent_stripe_ptr *)),\
39 		(const union bch_extent_entry *) (_entry),		\
40 		(union bch_extent_entry *) (_entry));			\
41 })
42 
43 #define extent_entry_next(_entry)					\
44 	((typeof(_entry)) ((void *) (_entry) + extent_entry_bytes(_entry)))
45 
46 #define extent_entry_next_safe(_entry, _end)				\
47 	(likely(__extent_entry_type(_entry) < BCH_EXTENT_ENTRY_MAX)	\
48 	 ? extent_entry_next(_entry)					\
49 	 : _end)
50 
51 static inline unsigned
52 __extent_entry_type(const union bch_extent_entry *e)
53 {
54 	return e->type ? __ffs(e->type) : BCH_EXTENT_ENTRY_MAX;
55 }
56 
57 static inline enum bch_extent_entry_type
58 extent_entry_type(const union bch_extent_entry *e)
59 {
60 	int ret = __ffs(e->type);
61 
62 	EBUG_ON(ret < 0 || ret >= BCH_EXTENT_ENTRY_MAX);
63 
64 	return ret;
65 }
66 
67 static inline size_t extent_entry_bytes(const union bch_extent_entry *entry)
68 {
69 	switch (extent_entry_type(entry)) {
70 #define x(f, n)						\
71 	case BCH_EXTENT_ENTRY_##f:			\
72 		return sizeof(struct bch_extent_##f);
73 	BCH_EXTENT_ENTRY_TYPES()
74 #undef x
75 	default:
76 		BUG();
77 	}
78 }
79 
80 static inline size_t extent_entry_u64s(const union bch_extent_entry *entry)
81 {
82 	return extent_entry_bytes(entry) / sizeof(u64);
83 }
84 
85 static inline void __extent_entry_insert(struct bkey_i *k,
86 					 union bch_extent_entry *dst,
87 					 union bch_extent_entry *new)
88 {
89 	union bch_extent_entry *end = bkey_val_end(bkey_i_to_s(k));
90 
91 	memmove_u64s_up_small((u64 *) dst + extent_entry_u64s(new),
92 			      dst, (u64 *) end - (u64 *) dst);
93 	k->k.u64s += extent_entry_u64s(new);
94 	memcpy_u64s_small(dst, new, extent_entry_u64s(new));
95 }
96 
97 static inline void extent_entry_drop(struct bkey_s k, union bch_extent_entry *entry)
98 {
99 	union bch_extent_entry *next = extent_entry_next(entry);
100 
101 	/* stripes have ptrs, but their layout doesn't work with this code */
102 	BUG_ON(k.k->type == KEY_TYPE_stripe);
103 
104 	memmove_u64s_down(entry, next,
105 			  (u64 *) bkey_val_end(k) - (u64 *) next);
106 	k.k->u64s -= (u64 *) next - (u64 *) entry;
107 }
108 
109 static inline bool extent_entry_is_ptr(const union bch_extent_entry *e)
110 {
111 	return __extent_entry_type(e) == BCH_EXTENT_ENTRY_ptr;
112 }
113 
114 static inline bool extent_entry_is_stripe_ptr(const union bch_extent_entry *e)
115 {
116 	return __extent_entry_type(e) == BCH_EXTENT_ENTRY_stripe_ptr;
117 }
118 
119 static inline bool extent_entry_is_crc(const union bch_extent_entry *e)
120 {
121 	switch (__extent_entry_type(e)) {
122 	case BCH_EXTENT_ENTRY_crc32:
123 	case BCH_EXTENT_ENTRY_crc64:
124 	case BCH_EXTENT_ENTRY_crc128:
125 		return true;
126 	default:
127 		return false;
128 	}
129 }
130 
131 union bch_extent_crc {
132 	u8				type;
133 	struct bch_extent_crc32		crc32;
134 	struct bch_extent_crc64		crc64;
135 	struct bch_extent_crc128	crc128;
136 };
137 
138 #define __entry_to_crc(_entry)						\
139 	__builtin_choose_expr(						\
140 		type_is_exact(_entry, const union bch_extent_entry *),	\
141 		(const union bch_extent_crc *) (_entry),		\
142 		(union bch_extent_crc *) (_entry))
143 
144 #define entry_to_crc(_entry)						\
145 ({									\
146 	EBUG_ON((_entry) && !extent_entry_is_crc(_entry));		\
147 									\
148 	__entry_to_crc(_entry);						\
149 })
150 
151 static inline struct bch_extent_crc_unpacked
152 bch2_extent_crc_unpack(const struct bkey *k, const union bch_extent_crc *crc)
153 {
154 #define common_fields(_crc)						\
155 		.csum_type		= _crc.csum_type,		\
156 		.compression_type	= _crc.compression_type,	\
157 		.compressed_size	= _crc._compressed_size + 1,	\
158 		.uncompressed_size	= _crc._uncompressed_size + 1,	\
159 		.offset			= _crc.offset,			\
160 		.live_size		= k->size
161 
162 	if (!crc)
163 		return (struct bch_extent_crc_unpacked) {
164 			.compressed_size	= k->size,
165 			.uncompressed_size	= k->size,
166 			.live_size		= k->size,
167 		};
168 
169 	switch (extent_entry_type(to_entry(crc))) {
170 	case BCH_EXTENT_ENTRY_crc32: {
171 		struct bch_extent_crc_unpacked ret = (struct bch_extent_crc_unpacked) {
172 			common_fields(crc->crc32),
173 		};
174 
175 		*((__le32 *) &ret.csum.lo) = (__le32 __force) crc->crc32.csum;
176 		return ret;
177 	}
178 	case BCH_EXTENT_ENTRY_crc64: {
179 		struct bch_extent_crc_unpacked ret = (struct bch_extent_crc_unpacked) {
180 			common_fields(crc->crc64),
181 			.nonce			= crc->crc64.nonce,
182 			.csum.lo		= (__force __le64) crc->crc64.csum_lo,
183 		};
184 
185 		*((__le16 *) &ret.csum.hi) = (__le16 __force) crc->crc64.csum_hi;
186 
187 		return ret;
188 	}
189 	case BCH_EXTENT_ENTRY_crc128: {
190 		struct bch_extent_crc_unpacked ret = (struct bch_extent_crc_unpacked) {
191 			common_fields(crc->crc128),
192 			.nonce			= crc->crc128.nonce,
193 			.csum			= crc->crc128.csum,
194 		};
195 
196 		return ret;
197 	}
198 	default:
199 		BUG();
200 	}
201 #undef common_fields
202 }
203 
204 static inline bool crc_is_compressed(struct bch_extent_crc_unpacked crc)
205 {
206 	return (crc.compression_type != BCH_COMPRESSION_TYPE_none &&
207 		crc.compression_type != BCH_COMPRESSION_TYPE_incompressible);
208 }
209 
210 static inline bool crc_is_encoded(struct bch_extent_crc_unpacked crc)
211 {
212 	return crc.csum_type != BCH_CSUM_none || crc_is_compressed(crc);
213 }
214 
215 /* bkey_ptrs: generically over any key type that has ptrs */
216 
217 struct bkey_ptrs_c {
218 	const union bch_extent_entry	*start;
219 	const union bch_extent_entry	*end;
220 };
221 
222 struct bkey_ptrs {
223 	union bch_extent_entry	*start;
224 	union bch_extent_entry	*end;
225 };
226 
227 static inline struct bkey_ptrs_c bch2_bkey_ptrs_c(struct bkey_s_c k)
228 {
229 	switch (k.k->type) {
230 	case KEY_TYPE_btree_ptr: {
231 		struct bkey_s_c_btree_ptr e = bkey_s_c_to_btree_ptr(k);
232 
233 		return (struct bkey_ptrs_c) {
234 			to_entry(&e.v->start[0]),
235 			to_entry(extent_entry_last(e))
236 		};
237 	}
238 	case KEY_TYPE_extent: {
239 		struct bkey_s_c_extent e = bkey_s_c_to_extent(k);
240 
241 		return (struct bkey_ptrs_c) {
242 			e.v->start,
243 			extent_entry_last(e)
244 		};
245 	}
246 	case KEY_TYPE_stripe: {
247 		struct bkey_s_c_stripe s = bkey_s_c_to_stripe(k);
248 
249 		return (struct bkey_ptrs_c) {
250 			to_entry(&s.v->ptrs[0]),
251 			to_entry(&s.v->ptrs[s.v->nr_blocks]),
252 		};
253 	}
254 	case KEY_TYPE_reflink_v: {
255 		struct bkey_s_c_reflink_v r = bkey_s_c_to_reflink_v(k);
256 
257 		return (struct bkey_ptrs_c) {
258 			r.v->start,
259 			bkey_val_end(r),
260 		};
261 	}
262 	case KEY_TYPE_btree_ptr_v2: {
263 		struct bkey_s_c_btree_ptr_v2 e = bkey_s_c_to_btree_ptr_v2(k);
264 
265 		return (struct bkey_ptrs_c) {
266 			to_entry(&e.v->start[0]),
267 			to_entry(extent_entry_last(e))
268 		};
269 	}
270 	default:
271 		return (struct bkey_ptrs_c) { NULL, NULL };
272 	}
273 }
274 
275 static inline struct bkey_ptrs bch2_bkey_ptrs(struct bkey_s k)
276 {
277 	struct bkey_ptrs_c p = bch2_bkey_ptrs_c(k.s_c);
278 
279 	return (struct bkey_ptrs) {
280 		(void *) p.start,
281 		(void *) p.end
282 	};
283 }
284 
285 #define __bkey_extent_entry_for_each_from(_start, _end, _entry)		\
286 	for ((_entry) = (_start);					\
287 	     (_entry) < (_end);						\
288 	     (_entry) = extent_entry_next_safe(_entry, _end))
289 
290 #define __bkey_ptr_next(_ptr, _end)					\
291 ({									\
292 	typeof(_end) _entry;						\
293 									\
294 	__bkey_extent_entry_for_each_from(to_entry(_ptr), _end, _entry)	\
295 		if (extent_entry_is_ptr(_entry))			\
296 			break;						\
297 									\
298 	_entry < (_end) ? entry_to_ptr(_entry) : NULL;			\
299 })
300 
301 #define bkey_extent_entry_for_each_from(_p, _entry, _start)		\
302 	__bkey_extent_entry_for_each_from(_start, (_p).end, _entry)
303 
304 #define bkey_extent_entry_for_each(_p, _entry)				\
305 	bkey_extent_entry_for_each_from(_p, _entry, _p.start)
306 
307 #define __bkey_for_each_ptr(_start, _end, _ptr)				\
308 	for (typeof(_start) (_ptr) = (_start);				\
309 	     ((_ptr) = __bkey_ptr_next(_ptr, _end));			\
310 	     (_ptr)++)
311 
312 #define bkey_ptr_next(_p, _ptr)						\
313 	__bkey_ptr_next(_ptr, (_p).end)
314 
315 #define bkey_for_each_ptr(_p, _ptr)					\
316 	__bkey_for_each_ptr(&(_p).start->ptr, (_p).end, _ptr)
317 
318 #define __bkey_ptr_next_decode(_k, _end, _ptr, _entry)			\
319 ({									\
320 	__label__ out;							\
321 									\
322 	(_ptr).idx	= 0;						\
323 	(_ptr).has_ec	= false;					\
324 									\
325 	__bkey_extent_entry_for_each_from(_entry, _end, _entry)		\
326 		switch (__extent_entry_type(_entry)) {			\
327 		case BCH_EXTENT_ENTRY_ptr:				\
328 			(_ptr).ptr		= _entry->ptr;		\
329 			goto out;					\
330 		case BCH_EXTENT_ENTRY_crc32:				\
331 		case BCH_EXTENT_ENTRY_crc64:				\
332 		case BCH_EXTENT_ENTRY_crc128:				\
333 			(_ptr).crc = bch2_extent_crc_unpack(_k,		\
334 					entry_to_crc(_entry));		\
335 			break;						\
336 		case BCH_EXTENT_ENTRY_stripe_ptr:			\
337 			(_ptr).ec = _entry->stripe_ptr;			\
338 			(_ptr).has_ec	= true;				\
339 			break;						\
340 		default:						\
341 			/* nothing */					\
342 			break;						\
343 		}							\
344 out:									\
345 	_entry < (_end);						\
346 })
347 
348 #define __bkey_for_each_ptr_decode(_k, _start, _end, _ptr, _entry)	\
349 	for ((_ptr).crc = bch2_extent_crc_unpack(_k, NULL),		\
350 	     (_entry) = _start;						\
351 	     __bkey_ptr_next_decode(_k, _end, _ptr, _entry);		\
352 	     (_entry) = extent_entry_next_safe(_entry, _end))
353 
354 #define bkey_for_each_ptr_decode(_k, _p, _ptr, _entry)			\
355 	__bkey_for_each_ptr_decode(_k, (_p).start, (_p).end,		\
356 				   _ptr, _entry)
357 
358 #define bkey_crc_next(_k, _start, _end, _crc, _iter)			\
359 ({									\
360 	__bkey_extent_entry_for_each_from(_iter, _end, _iter)		\
361 		if (extent_entry_is_crc(_iter)) {			\
362 			(_crc) = bch2_extent_crc_unpack(_k,		\
363 						entry_to_crc(_iter));	\
364 			break;						\
365 		}							\
366 									\
367 	(_iter) < (_end);						\
368 })
369 
370 #define __bkey_for_each_crc(_k, _start, _end, _crc, _iter)		\
371 	for ((_crc) = bch2_extent_crc_unpack(_k, NULL),			\
372 	     (_iter) = (_start);					\
373 	     bkey_crc_next(_k, _start, _end, _crc, _iter);		\
374 	     (_iter) = extent_entry_next(_iter))
375 
376 #define bkey_for_each_crc(_k, _p, _crc, _iter)				\
377 	__bkey_for_each_crc(_k, (_p).start, (_p).end, _crc, _iter)
378 
379 /* Iterate over pointers in KEY_TYPE_extent: */
380 
381 #define extent_for_each_entry_from(_e, _entry, _start)			\
382 	__bkey_extent_entry_for_each_from(_start,			\
383 				extent_entry_last(_e), _entry)
384 
385 #define extent_for_each_entry(_e, _entry)				\
386 	extent_for_each_entry_from(_e, _entry, (_e).v->start)
387 
388 #define extent_ptr_next(_e, _ptr)					\
389 	__bkey_ptr_next(_ptr, extent_entry_last(_e))
390 
391 #define extent_for_each_ptr(_e, _ptr)					\
392 	__bkey_for_each_ptr(&(_e).v->start->ptr, extent_entry_last(_e), _ptr)
393 
394 #define extent_for_each_ptr_decode(_e, _ptr, _entry)			\
395 	__bkey_for_each_ptr_decode((_e).k, (_e).v->start,		\
396 				   extent_entry_last(_e), _ptr, _entry)
397 
398 /* utility code common to all keys with pointers: */
399 
400 void bch2_mark_io_failure(struct bch_io_failures *,
401 			  struct extent_ptr_decoded *);
402 int bch2_bkey_pick_read_device(struct bch_fs *, struct bkey_s_c,
403 			       struct bch_io_failures *,
404 			       struct extent_ptr_decoded *);
405 
406 /* KEY_TYPE_btree_ptr: */
407 
408 int bch2_btree_ptr_invalid(struct bch_fs *, struct bkey_s_c,
409 			   enum bkey_invalid_flags, struct printbuf *);
410 void bch2_btree_ptr_to_text(struct printbuf *, struct bch_fs *,
411 			    struct bkey_s_c);
412 
413 int bch2_btree_ptr_v2_invalid(struct bch_fs *, struct bkey_s_c,
414 			      enum bkey_invalid_flags, struct printbuf *);
415 void bch2_btree_ptr_v2_to_text(struct printbuf *, struct bch_fs *, struct bkey_s_c);
416 void bch2_btree_ptr_v2_compat(enum btree_id, unsigned, unsigned,
417 			      int, struct bkey_s);
418 
419 #define bch2_bkey_ops_btree_ptr ((struct bkey_ops) {		\
420 	.key_invalid	= bch2_btree_ptr_invalid,		\
421 	.val_to_text	= bch2_btree_ptr_to_text,		\
422 	.swab		= bch2_ptr_swab,			\
423 	.trigger	= bch2_trigger_extent,			\
424 })
425 
426 #define bch2_bkey_ops_btree_ptr_v2 ((struct bkey_ops) {		\
427 	.key_invalid	= bch2_btree_ptr_v2_invalid,		\
428 	.val_to_text	= bch2_btree_ptr_v2_to_text,		\
429 	.swab		= bch2_ptr_swab,			\
430 	.compat		= bch2_btree_ptr_v2_compat,		\
431 	.trigger	= bch2_trigger_extent,			\
432 	.min_val_size	= 40,					\
433 })
434 
435 /* KEY_TYPE_extent: */
436 
437 bool bch2_extent_merge(struct bch_fs *, struct bkey_s, struct bkey_s_c);
438 
439 #define bch2_bkey_ops_extent ((struct bkey_ops) {		\
440 	.key_invalid	= bch2_bkey_ptrs_invalid,		\
441 	.val_to_text	= bch2_bkey_ptrs_to_text,		\
442 	.swab		= bch2_ptr_swab,			\
443 	.key_normalize	= bch2_extent_normalize,		\
444 	.key_merge	= bch2_extent_merge,			\
445 	.trigger	= bch2_trigger_extent,			\
446 })
447 
448 /* KEY_TYPE_reservation: */
449 
450 int bch2_reservation_invalid(struct bch_fs *, struct bkey_s_c,
451 			     enum bkey_invalid_flags, struct printbuf *);
452 void bch2_reservation_to_text(struct printbuf *, struct bch_fs *, struct bkey_s_c);
453 bool bch2_reservation_merge(struct bch_fs *, struct bkey_s, struct bkey_s_c);
454 
455 #define bch2_bkey_ops_reservation ((struct bkey_ops) {		\
456 	.key_invalid	= bch2_reservation_invalid,		\
457 	.val_to_text	= bch2_reservation_to_text,		\
458 	.key_merge	= bch2_reservation_merge,		\
459 	.trigger	= bch2_trigger_reservation,		\
460 	.min_val_size	= 8,					\
461 })
462 
463 /* Extent checksum entries: */
464 
465 bool bch2_can_narrow_extent_crcs(struct bkey_s_c,
466 				 struct bch_extent_crc_unpacked);
467 bool bch2_bkey_narrow_crcs(struct bkey_i *, struct bch_extent_crc_unpacked);
468 void bch2_extent_crc_append(struct bkey_i *,
469 			    struct bch_extent_crc_unpacked);
470 
471 /* Generic code for keys with pointers: */
472 
473 static inline bool bkey_is_btree_ptr(const struct bkey *k)
474 {
475 	switch (k->type) {
476 	case KEY_TYPE_btree_ptr:
477 	case KEY_TYPE_btree_ptr_v2:
478 		return true;
479 	default:
480 		return false;
481 	}
482 }
483 
484 static inline bool bkey_extent_is_direct_data(const struct bkey *k)
485 {
486 	switch (k->type) {
487 	case KEY_TYPE_btree_ptr:
488 	case KEY_TYPE_btree_ptr_v2:
489 	case KEY_TYPE_extent:
490 	case KEY_TYPE_reflink_v:
491 		return true;
492 	default:
493 		return false;
494 	}
495 }
496 
497 static inline bool bkey_extent_is_inline_data(const struct bkey *k)
498 {
499 	return  k->type == KEY_TYPE_inline_data ||
500 		k->type == KEY_TYPE_indirect_inline_data;
501 }
502 
503 static inline unsigned bkey_inline_data_offset(const struct bkey *k)
504 {
505 	switch (k->type) {
506 	case KEY_TYPE_inline_data:
507 		return sizeof(struct bch_inline_data);
508 	case KEY_TYPE_indirect_inline_data:
509 		return sizeof(struct bch_indirect_inline_data);
510 	default:
511 		BUG();
512 	}
513 }
514 
515 static inline unsigned bkey_inline_data_bytes(const struct bkey *k)
516 {
517 	return bkey_val_bytes(k) - bkey_inline_data_offset(k);
518 }
519 
520 #define bkey_inline_data_p(_k)	(((void *) (_k).v) + bkey_inline_data_offset((_k).k))
521 
522 static inline bool bkey_extent_is_data(const struct bkey *k)
523 {
524 	return  bkey_extent_is_direct_data(k) ||
525 		bkey_extent_is_inline_data(k) ||
526 		k->type == KEY_TYPE_reflink_p;
527 }
528 
529 /*
530  * Should extent be counted under inode->i_sectors?
531  */
532 static inline bool bkey_extent_is_allocation(const struct bkey *k)
533 {
534 	switch (k->type) {
535 	case KEY_TYPE_extent:
536 	case KEY_TYPE_reservation:
537 	case KEY_TYPE_reflink_p:
538 	case KEY_TYPE_reflink_v:
539 	case KEY_TYPE_inline_data:
540 	case KEY_TYPE_indirect_inline_data:
541 	case KEY_TYPE_error:
542 		return true;
543 	default:
544 		return false;
545 	}
546 }
547 
548 static inline bool bkey_extent_is_unwritten(struct bkey_s_c k)
549 {
550 	struct bkey_ptrs_c ptrs = bch2_bkey_ptrs_c(k);
551 
552 	bkey_for_each_ptr(ptrs, ptr)
553 		if (ptr->unwritten)
554 			return true;
555 	return false;
556 }
557 
558 static inline bool bkey_extent_is_reservation(struct bkey_s_c k)
559 {
560 	return k.k->type == KEY_TYPE_reservation ||
561 		bkey_extent_is_unwritten(k);
562 }
563 
564 static inline struct bch_devs_list bch2_bkey_devs(struct bkey_s_c k)
565 {
566 	struct bch_devs_list ret = (struct bch_devs_list) { 0 };
567 	struct bkey_ptrs_c p = bch2_bkey_ptrs_c(k);
568 
569 	bkey_for_each_ptr(p, ptr)
570 		ret.data[ret.nr++] = ptr->dev;
571 
572 	return ret;
573 }
574 
575 static inline struct bch_devs_list bch2_bkey_dirty_devs(struct bkey_s_c k)
576 {
577 	struct bch_devs_list ret = (struct bch_devs_list) { 0 };
578 	struct bkey_ptrs_c p = bch2_bkey_ptrs_c(k);
579 
580 	bkey_for_each_ptr(p, ptr)
581 		if (!ptr->cached)
582 			ret.data[ret.nr++] = ptr->dev;
583 
584 	return ret;
585 }
586 
587 static inline struct bch_devs_list bch2_bkey_cached_devs(struct bkey_s_c k)
588 {
589 	struct bch_devs_list ret = (struct bch_devs_list) { 0 };
590 	struct bkey_ptrs_c p = bch2_bkey_ptrs_c(k);
591 
592 	bkey_for_each_ptr(p, ptr)
593 		if (ptr->cached)
594 			ret.data[ret.nr++] = ptr->dev;
595 
596 	return ret;
597 }
598 
599 static inline unsigned bch2_bkey_ptr_data_type(struct bkey_s_c k, const struct bch_extent_ptr *ptr)
600 {
601 	switch (k.k->type) {
602 	case KEY_TYPE_btree_ptr:
603 	case KEY_TYPE_btree_ptr_v2:
604 		return BCH_DATA_btree;
605 	case KEY_TYPE_extent:
606 	case KEY_TYPE_reflink_v:
607 		return BCH_DATA_user;
608 	case KEY_TYPE_stripe: {
609 		struct bkey_s_c_stripe s = bkey_s_c_to_stripe(k);
610 
611 		BUG_ON(ptr < s.v->ptrs ||
612 		       ptr >= s.v->ptrs + s.v->nr_blocks);
613 
614 		return ptr >= s.v->ptrs + s.v->nr_blocks - s.v->nr_redundant
615 			? BCH_DATA_parity
616 			: BCH_DATA_user;
617 	}
618 	default:
619 		BUG();
620 	}
621 }
622 
623 unsigned bch2_bkey_nr_ptrs(struct bkey_s_c);
624 unsigned bch2_bkey_nr_ptrs_allocated(struct bkey_s_c);
625 unsigned bch2_bkey_nr_ptrs_fully_allocated(struct bkey_s_c);
626 bool bch2_bkey_is_incompressible(struct bkey_s_c);
627 unsigned bch2_bkey_sectors_compressed(struct bkey_s_c);
628 
629 unsigned bch2_bkey_replicas(struct bch_fs *, struct bkey_s_c);
630 unsigned bch2_extent_ptr_desired_durability(struct bch_fs *, struct extent_ptr_decoded *);
631 unsigned bch2_extent_ptr_durability(struct bch_fs *, struct extent_ptr_decoded *);
632 unsigned bch2_bkey_durability(struct bch_fs *, struct bkey_s_c);
633 
634 void bch2_bkey_drop_device(struct bkey_s, unsigned);
635 void bch2_bkey_drop_device_noerror(struct bkey_s, unsigned);
636 
637 const struct bch_extent_ptr *bch2_bkey_has_device_c(struct bkey_s_c, unsigned);
638 
639 static inline struct bch_extent_ptr *bch2_bkey_has_device(struct bkey_s k, unsigned dev)
640 {
641 	return (void *) bch2_bkey_has_device_c(k.s_c, dev);
642 }
643 
644 bool bch2_bkey_has_target(struct bch_fs *, struct bkey_s_c, unsigned);
645 
646 void bch2_bkey_extent_entry_drop(struct bkey_i *, union bch_extent_entry *);
647 
648 static inline void bch2_bkey_append_ptr(struct bkey_i *k, struct bch_extent_ptr ptr)
649 {
650 	struct bch_extent_ptr *dest;
651 
652 	EBUG_ON(bch2_bkey_has_device(bkey_i_to_s(k), ptr.dev));
653 
654 	switch (k->k.type) {
655 	case KEY_TYPE_btree_ptr:
656 	case KEY_TYPE_btree_ptr_v2:
657 	case KEY_TYPE_extent:
658 		EBUG_ON(bkey_val_u64s(&k->k) >= BKEY_EXTENT_VAL_U64s_MAX);
659 
660 		ptr.type = 1 << BCH_EXTENT_ENTRY_ptr;
661 		dest = (struct bch_extent_ptr *)((void *) &k->v + bkey_val_bytes(&k->k));
662 		*dest = ptr;
663 		k->k.u64s++;
664 		break;
665 	default:
666 		BUG();
667 	}
668 }
669 
670 void bch2_extent_ptr_decoded_append(struct bkey_i *,
671 				    struct extent_ptr_decoded *);
672 union bch_extent_entry *bch2_bkey_drop_ptr_noerror(struct bkey_s,
673 						   struct bch_extent_ptr *);
674 union bch_extent_entry *bch2_bkey_drop_ptr(struct bkey_s,
675 					   struct bch_extent_ptr *);
676 
677 #define bch2_bkey_drop_ptrs(_k, _ptr, _cond)				\
678 do {									\
679 	struct bkey_ptrs _ptrs = bch2_bkey_ptrs(_k);			\
680 									\
681 	_ptr = &_ptrs.start->ptr;					\
682 									\
683 	while ((_ptr = bkey_ptr_next(_ptrs, _ptr))) {			\
684 		if (_cond) {						\
685 			_ptr = (void *) bch2_bkey_drop_ptr(_k, _ptr);	\
686 			_ptrs = bch2_bkey_ptrs(_k);			\
687 			continue;					\
688 		}							\
689 									\
690 		(_ptr)++;						\
691 	}								\
692 } while (0)
693 
694 bool bch2_bkey_matches_ptr(struct bch_fs *, struct bkey_s_c,
695 			   struct bch_extent_ptr, u64);
696 bool bch2_extents_match(struct bkey_s_c, struct bkey_s_c);
697 struct bch_extent_ptr *
698 bch2_extent_has_ptr(struct bkey_s_c, struct extent_ptr_decoded, struct bkey_s);
699 
700 void bch2_extent_ptr_set_cached(struct bkey_s, struct bch_extent_ptr *);
701 
702 bool bch2_extent_normalize(struct bch_fs *, struct bkey_s);
703 void bch2_bkey_ptrs_to_text(struct printbuf *, struct bch_fs *,
704 			    struct bkey_s_c);
705 int bch2_bkey_ptrs_invalid(struct bch_fs *, struct bkey_s_c,
706 			   enum bkey_invalid_flags, struct printbuf *);
707 
708 void bch2_ptr_swab(struct bkey_s);
709 
710 const struct bch_extent_rebalance *bch2_bkey_rebalance_opts(struct bkey_s_c);
711 unsigned bch2_bkey_ptrs_need_rebalance(struct bch_fs *, struct bkey_s_c,
712 				       unsigned, unsigned);
713 bool bch2_bkey_needs_rebalance(struct bch_fs *, struct bkey_s_c);
714 
715 int bch2_bkey_set_needs_rebalance(struct bch_fs *, struct bkey_i *,
716 				  struct bch_io_opts *);
717 
718 /* Generic extent code: */
719 
720 enum bch_extent_overlap {
721 	BCH_EXTENT_OVERLAP_ALL		= 0,
722 	BCH_EXTENT_OVERLAP_BACK		= 1,
723 	BCH_EXTENT_OVERLAP_FRONT	= 2,
724 	BCH_EXTENT_OVERLAP_MIDDLE	= 3,
725 };
726 
727 /* Returns how k overlaps with m */
728 static inline enum bch_extent_overlap bch2_extent_overlap(const struct bkey *k,
729 							  const struct bkey *m)
730 {
731 	int cmp1 = bkey_lt(k->p, m->p);
732 	int cmp2 = bkey_gt(bkey_start_pos(k), bkey_start_pos(m));
733 
734 	return (cmp1 << 1) + cmp2;
735 }
736 
737 int bch2_cut_front_s(struct bpos, struct bkey_s);
738 int bch2_cut_back_s(struct bpos, struct bkey_s);
739 
740 static inline void bch2_cut_front(struct bpos where, struct bkey_i *k)
741 {
742 	bch2_cut_front_s(where, bkey_i_to_s(k));
743 }
744 
745 static inline void bch2_cut_back(struct bpos where, struct bkey_i *k)
746 {
747 	bch2_cut_back_s(where, bkey_i_to_s(k));
748 }
749 
750 /**
751  * bch_key_resize - adjust size of @k
752  *
753  * bkey_start_offset(k) will be preserved, modifies where the extent ends
754  */
755 static inline void bch2_key_resize(struct bkey *k, unsigned new_size)
756 {
757 	k->p.offset -= k->size;
758 	k->p.offset += new_size;
759 	k->size = new_size;
760 }
761 
762 #endif /* _BCACHEFS_EXTENTS_H */
763