rework parsing of interupt-map in interrupt node.
[lunaix-os.git] / lunaix-os / includes / lunaix / blkio.h
1 #ifndef __LUNAIX_BLKIO_H
2 #define __LUNAIX_BLKIO_H
3
4 #include <lunaix/buffer.h>
5 #include <lunaix/buffer.h>
6 #include <lunaix/ds/llist.h>
7 #include <lunaix/ds/waitq.h>
8 #include <lunaix/ds/mutex.h>
9 #include <lunaix/types.h>
10
11 #define BLKIO_WRITE 0x1
12 #define BLKIO_ERROR 0x2
13
14 #define BLKIO_BUSY 0x4
15 #define BLKIO_PENDING 0x8
16 // Free on complete
17 #define BLKIO_FOC 0x10
18 #define BLKIO_SHOULD_WAIT 0x20
19
20 #define BLKIO_WAIT 0x1
21 #define BLKIO_NOWAIT 0
22 #define BLKIO_NOASYNC 0x2
23
24 #define BLKIO_SCHED_IDEL 0x1
25
26 struct blkio_req;
27
28 typedef void (*blkio_cb)(struct blkio_req*);
29 typedef void (*req_handler)(struct blkio_req*);
30
31 struct blkio_req
32 {
33     struct llist_header reqs;
34     struct blkio_context* io_ctx;
35     struct vecbuf* vbuf;
36     u32_t flags;
37     waitq_t wait;
38     u64_t blk_addr;
39     void* evt_args;
40     blkio_cb completed;
41     int errcode;
42 };
43
44 struct blkio_context
45 {
46     struct llist_header queue;
47
48     struct
49     {
50         u32_t seektime;
51         u32_t rotdelay;
52     } metrics;
53
54     req_handler handle_one;
55     u32_t state;
56     u32_t busy;
57     void* driver;
58
59     mutex_t lock;
60 };
61
62 static inline void
63 blkio_lock(struct blkio_context* contex)
64 {
65     mutex_lock(&contex->lock);
66 }
67
68 static inline void
69 blkio_unlock(struct blkio_context* contex)
70 {
71     mutex_unlock(&contex->lock);
72 }
73
74 static inline bool
75 blkio_stalled(struct blkio_context* contex)
76 {
77     return !contex->busy;
78 }
79
80 void
81 blkio_init();
82
83 /**
84  * @brief Vectorized read request
85  *
86  * @param vbuf
87  * @param start_lba
88  * @param completed
89  * @param evt_args
90  * @param options
91  * @return struct blkio_req*
92  */
93 struct blkio_req*
94 blkio_vrd(struct vecbuf* vbuf,
95           u64_t start_lba,
96           blkio_cb completed,
97           void* evt_args,
98           u32_t options);
99
100 /**
101  * @brief Vectorized write request
102  *
103  * @param vbuf
104  * @param start_lba
105  * @param completed
106  * @param evt_args
107  * @param options
108  * @return struct blkio_req*
109  */
110 struct blkio_req*
111 blkio_vwr(struct vecbuf* vbuf,
112           u64_t start_lba,
113           blkio_cb completed,
114           void* evt_args,
115           u32_t options);
116
117 /**
118  * @brief Vectorized request (no write/read preference)
119  *
120  * @param vbuf
121  * @param start_lba
122  * @param completed
123  * @param evt_args
124  * @param options
125  * @return struct blkio_req*
126  */
127 static inline struct blkio_req*
128 blkio_vreq(struct vecbuf* buffer,
129           u64_t start_lba,
130           blkio_cb completed,
131           void* evt_args,
132           u32_t options) {
133     /*
134         This is currently aliased to blkio_vrd. Although `no preference`
135         does essentially mean `default read`, the blkio_vreq just used
136         to enhance readability
137     */
138     return blkio_vrd(buffer, start_lba, completed, evt_args, options);
139 }
140
141
142 /**
143  * @brief Bind a block IO context to request
144  *
145  * @param ctx
146  * @param req
147  */
148 static inline void
149 blkio_bindctx(struct blkio_req* req, struct blkio_context* ctx)
150 {
151     req->io_ctx = ctx;
152 }
153
154 /**
155  * @brief Set block IO request to read
156  *
157  * @param ctx
158  * @param req
159  */
160 static inline void
161 blkio_setread(struct blkio_req* req)
162 {
163     if ((req->flags & BLKIO_PENDING)) {
164         return;
165     }
166     
167     req->flags &= ~BLKIO_WRITE;
168 }
169
170 /**
171  * @brief Set block IO request to write
172  *
173  * @param ctx
174  * @param req
175  */
176 static inline void
177 blkio_setwrite(struct blkio_req* req)
178 {
179     if ((req->flags & BLKIO_PENDING)) {
180         return;
181     }
182
183     req->flags |= BLKIO_WRITE;
184 }
185
186 /**
187  * @brief Set callback when request complete
188  * 
189  * @param req 
190  * @param on_completed 
191  */
192 static inline void
193 blkio_when_completed(struct blkio_req* req, blkio_cb on_completed)
194 {
195     req->completed = on_completed;
196 }
197
198 static inline bool
199 blkio_is_pending(struct blkio_req* req)
200 {
201     return (req->flags & BLKIO_PENDING);
202 }
203
204 /**
205  * @brief Mark request to be freed-on-completion (FOC)
206  * 
207  * @param req 
208  */
209 static inline void
210 blkio_mark_foc(struct blkio_req* req)
211 {
212     req->flags |= BLKIO_FOC;
213 }
214
215 /**
216  * @brief Mark request to be not-freed-on-completion (nFOC)
217  * 
218  * @param req 
219  */
220 static inline void
221 blkio_mark_nfoc(struct blkio_req* req)
222 {
223     req->flags &= ~BLKIO_FOC;
224 }
225
226 int
227 blkio_read_aligned(struct blkio_context* ctx, 
228                    unsigned long lba, void* block, size_t n_blk);
229
230 int
231 blkio_read(struct blkio_context* ctx, 
232            unsigned long offset, void* block, size_t len);
233
234 int
235 blkio_write_aligned(struct blkio_context* ctx, 
236                     unsigned long lba, void* block, size_t n_blk);
237
238 int
239 blkio_read(struct blkio_context* ctx, 
240            unsigned long offset, void* block, size_t len);
241
242 void
243 blkio_free_req(struct blkio_req* req);
244
245 /**
246  * @brief Commit an IO request to scheduler.
247  *
248  * @param ctx
249  * @param req
250  */
251 void
252 blkio_commit(struct blkio_req* req, int options);
253
254
255 /**
256  * @brief Schedule an IO request to be handled.
257  *
258  * @param ctx
259  */
260 void
261 blkio_schedule(struct blkio_context* ctx);
262
263 /**
264  * @brief Notify the scheduler when request is completed, either successful or
265  * failed.
266  *
267  * @param ctx
268  * @param req
269  */
270 void
271 blkio_complete(struct blkio_req* req);
272
273 /**
274  * @brief Create a new block IO scheduling context
275  *
276  * @param handler Handler to handle request
277  * @return struct blkio_context*
278  */
279 struct blkio_context*
280 blkio_newctx(req_handler handler);
281
282 #endif /* __LUNAIX_BLKIO_H */