]> git.sesse.net Git - bcachefs-tools-debian/blob - libbcachefs/alloc_foreground.h
Add upstream files
[bcachefs-tools-debian] / libbcachefs / alloc_foreground.h
1 /* SPDX-License-Identifier: GPL-2.0 */
2 #ifndef _BCACHEFS_ALLOC_FOREGROUND_H
3 #define _BCACHEFS_ALLOC_FOREGROUND_H
4
5 #include "bcachefs.h"
6 #include "alloc_types.h"
7
8 #include <linux/hash.h>
9
10 struct bkey;
11 struct bch_dev;
12 struct bch_fs;
13 struct bch_devs_List;
14
15 enum bucket_alloc_ret {
16         ALLOC_SUCCESS,
17         OPEN_BUCKETS_EMPTY,
18         FREELIST_EMPTY,         /* Allocator thread not keeping up */
19         INSUFFICIENT_DEVICES,
20 };
21
22 struct dev_alloc_list {
23         unsigned        nr;
24         u8              devs[BCH_SB_MEMBERS_MAX];
25 };
26
27 struct dev_alloc_list bch2_dev_alloc_list(struct bch_fs *,
28                                           struct dev_stripe_state *,
29                                           struct bch_devs_mask *);
30 void bch2_dev_stripe_increment(struct bch_dev *, struct dev_stripe_state *);
31
32 long bch2_bucket_alloc_new_fs(struct bch_dev *);
33
34 struct open_bucket *bch2_bucket_alloc(struct bch_fs *, struct bch_dev *,
35                                       enum alloc_reserve, bool,
36                                       struct closure *);
37
38 static inline void ob_push(struct bch_fs *c, struct open_buckets *obs,
39                            struct open_bucket *ob)
40 {
41         BUG_ON(obs->nr >= ARRAY_SIZE(obs->v));
42
43         obs->v[obs->nr++] = ob - c->open_buckets;
44 }
45
46 #define open_bucket_for_each(_c, _obs, _ob, _i)                         \
47         for ((_i) = 0;                                                  \
48              (_i) < (_obs)->nr &&                                       \
49              ((_ob) = (_c)->open_buckets + (_obs)->v[_i], true);        \
50              (_i)++)
51
52 static inline struct open_bucket *ec_open_bucket(struct bch_fs *c,
53                                                  struct open_buckets *obs)
54 {
55         struct open_bucket *ob;
56         unsigned i;
57
58         open_bucket_for_each(c, obs, ob, i)
59                 if (ob->ec)
60                         return ob;
61
62         return NULL;
63 }
64
65 void bch2_open_bucket_write_error(struct bch_fs *,
66                         struct open_buckets *, unsigned);
67
68 void __bch2_open_bucket_put(struct bch_fs *, struct open_bucket *);
69
70 static inline void bch2_open_bucket_put(struct bch_fs *c, struct open_bucket *ob)
71 {
72         if (atomic_dec_and_test(&ob->pin))
73                 __bch2_open_bucket_put(c, ob);
74 }
75
76 static inline void bch2_open_buckets_put(struct bch_fs *c,
77                                          struct open_buckets *ptrs)
78 {
79         struct open_bucket *ob;
80         unsigned i;
81
82         open_bucket_for_each(c, ptrs, ob, i)
83                 bch2_open_bucket_put(c, ob);
84         ptrs->nr = 0;
85 }
86
87 static inline void bch2_open_bucket_get(struct bch_fs *c,
88                                         struct write_point *wp,
89                                         struct open_buckets *ptrs)
90 {
91         struct open_bucket *ob;
92         unsigned i;
93
94         open_bucket_for_each(c, &wp->ptrs, ob, i) {
95                 ob->type = wp->type;
96                 atomic_inc(&ob->pin);
97                 ob_push(c, ptrs, ob);
98         }
99 }
100
101 enum bucket_alloc_ret
102 bch2_bucket_alloc_set(struct bch_fs *, struct open_buckets *,
103                       struct dev_stripe_state *, struct bch_devs_mask *,
104                       unsigned, unsigned *, bool *, enum alloc_reserve,
105                       unsigned, struct closure *);
106
107 struct write_point *bch2_alloc_sectors_start(struct bch_fs *,
108                                              unsigned, unsigned,
109                                              struct write_point_specifier,
110                                              struct bch_devs_list *,
111                                              unsigned, unsigned,
112                                              enum alloc_reserve,
113                                              unsigned,
114                                              struct closure *);
115
116 void bch2_alloc_sectors_append_ptrs(struct bch_fs *, struct write_point *,
117                                     struct bkey_i *, unsigned);
118 void bch2_alloc_sectors_done(struct bch_fs *, struct write_point *);
119
120 void bch2_open_buckets_stop_dev(struct bch_fs *, struct bch_dev *,
121                                 struct open_buckets *);
122
123 void bch2_writepoint_stop(struct bch_fs *, struct bch_dev *,
124                           struct write_point *);
125
126 static inline struct write_point_specifier writepoint_hashed(unsigned long v)
127 {
128         return (struct write_point_specifier) { .v = v | 1 };
129 }
130
131 static inline struct write_point_specifier writepoint_ptr(struct write_point *wp)
132 {
133         return (struct write_point_specifier) { .v = (unsigned long) wp };
134 }
135
136 void bch2_fs_allocator_foreground_init(struct bch_fs *);
137
138 #endif /* _BCACHEFS_ALLOC_FOREGROUND_H */