1 // SPDX-License-Identifier: MIT or LGPL-2.1-only
2
3 /**
4 * @file ublksrv.h
5 *
6 * libublksrv APIs
7 *
8 * This header define the interfaces of libublksrv
9 */
10
11 #ifndef UBLKSRV_INC_H
12 #define UBLKSRV_INC_H
13
14 #include <stdbool.h>
15 #include <assert.h>
16
17 #include "liburing.h"
18
19 #ifdef __cplusplus
20 extern "C" {
21 #endif
22
23 #include "ublk_cmd.h"
24
25 #define MAX_NR_HW_QUEUES 32
26 #define MAX_QD UBLK_MAX_QUEUE_DEPTH
27 #define MAX_BUF_SIZE (32U << 20)
28
29 #define DEF_NR_HW_QUEUES 1
30 #define DEF_QD 128
31 #define DEF_BUF_SIZE (512 << 10)
32
33 /************ stored in ublksrv_ctrl_dev_info->ublksrv_flags *******/
34 /*
35 * target may not use io_uring for handling io, so eventfd is required
36 * for wakeup io command io_uring context
37 */
38 #define UBLKSRV_F_NEED_EVENTFD (1UL << 1)
39
40 struct io_uring;
41 struct io_uring_cqe;
42 struct ublksrv_aio_ctx;
43 struct ublksrv_ctrl_dev;
44
45 /**
46 * Generic data for creating one ublk control device, which is used for
47 * sending control commands to /dev/ublk-control.
48 *
49 * Control commands(UBLK_CMD_*) are defined in ublk_cmd.h.
50 */
51 struct ublksrv_dev_data {
52 int dev_id;
53 unsigned max_io_buf_bytes;
54 unsigned short nr_hw_queues;
55 unsigned short queue_depth;
56 const char *tgt_type;
57 const struct ublksrv_tgt_type *tgt_ops;
58 int tgt_argc;
59 char **tgt_argv;
60 const char *run_dir;
61 unsigned long flags;
62 unsigned long ublksrv_flags;
63 unsigned long reserved[7];
64 };
65
66 /**
67 * IO data passed to target io handling callbacks, such as
68 * ->handle_io_async() and ->tgt_io_done().
69 */
70 struct ublk_io_data {
71 /** tag of this io data, unique in queue wide */
72 int tag;
73 unsigned int pad;
74
75 /** io description from ublk driver */
76 const struct ublksrv_io_desc *iod;
77
78 /**
79 * IO private data, created in ublksrv_queue_init(),
80 * data size is specified in ublksrv_tgt_info.io_data_size
81 */
82 void *private_data;
83 };
84
85 /* queue state is only retrieved via ublksrv_queue_state() API */
86 #define UBLKSRV_QUEUE_STOPPING (1U << 0)
87 #define UBLKSRV_QUEUE_IDLE (1U << 1)
88 #define UBLKSRV_QUEUE_IOCTL_OP (1U << 2)
89 #define UBLKSRV_USER_COPY (1U << 3)
90
91 /**
92 * ublksrv_queue is 1:1 mapping with ublk driver's blk-mq queue, and
93 * has same queue depth with ublk driver's blk-mq queue.
94 */
95 struct ublksrv_queue {
96 /** queue id */
97 int q_id;
98
99 /** So far, all queues in same device has same depth */
100 int q_depth;
101
102 /** io uring for handling io commands() from ublk driver */
103 struct io_uring *ring_ptr;
104
105 /** which device this queue belongs to */
106 const struct ublksrv_dev *dev;
107
108 /** queue's private data, passed from ublksrv_queue_init() */
109 void *private_data;
110 };
111
112 struct ublksrv_tgt_type;
113
114 #define UBLKSRV_TGT_MAX_FDS 32
115
116 /**
117 *
118 * ublksrv_tgt_info: target data
119 *
120 */
121 struct ublksrv_tgt_info {
122 /** device size */
123 unsigned long long dev_size;
124
125 /**
126 * target ring depth, for handling target IOs
127 */
128 unsigned int tgt_ring_depth;
129
130 /** how many FDs regisgered */
131 unsigned int nr_fds;
132
133 /** file descriptor table */
134 int fds[UBLKSRV_TGT_MAX_FDS];
135
136 /** target private data */
137 void *tgt_data;
138
139 /**
140 * Extra IO slots for each queue, target code can reserve some
141 * slots for handling internal IO, such as meta data IO, then
142 * ublk_io instances can be assigned for these extra IOs.
143 *
144 * IO slot is useful for storing coroutine data which is for
145 * handling this (meta) IO.
146 */
147 unsigned int extra_ios;
148
149 /** size of io private data */
150 unsigned int io_data_size;
151
152 /**
153 * target io handling type, target main job is to implement
154 * callbacks defined in this type
155 */
156 const struct ublksrv_tgt_type *ops;
157
158 /**
159 * If target needs to override default max workers for io_uring,
160 * initialize io_wq_max_workers with proper value, otherwise
161 * keep them as zero
162 */
163 unsigned int iowq_max_workers[2];
164
165 unsigned long reserved[4];
166 };
167
168 /**
169 * ublksrv device
170 */
171 struct ublksrv_dev {
172 /** device data */
173 struct ublksrv_tgt_info tgt;
174 };
175
176 /**
177 *
178 * ublksrv_tgt_type: target type
179 *
180 */
181 struct ublksrv_tgt_type {
182 /**
183 * One IO request comes from /dev/ublkbN, so notify target code
184 * for handling the IO. Inside target code, the IO can be handled
185 * with our io_uring too, if this is true, ->tgt_io_done callback
186 * has to be implemented. Otherwise, target can implement
187 * ->handle_event() for processing io completion there.
188 *
189 * Required.
190 */
191 int (*handle_io_async)(const struct ublksrv_queue *,
192 const struct ublk_io_data *io);
193
194 /**
195 * target io is handled by our io_uring, and once the target io
196 * is completed, this callback is called.
197 *
198 * Optional, only required iff this target io is handled by ublksrv's
199 * io_uring.
200 */
201 void (*tgt_io_done)(const struct ublksrv_queue *,
202 const struct ublk_io_data *io,
203 const struct io_uring_cqe *);
204
205 /**
206 * Someone has written to our eventfd, so let target handle the
207 * event, most of times, it is for handling io completion by
208 * calling ublksrv_complete_io() which has to be run in ubq_daemon
209 * context.
210 *
211 * Follows the typical scenario:
212 *
213 * 1) one target io is completed in target pthread context, so
214 * target code calls ublksrv_queue_send_event for notifying ubq
215 * daemon
216 *
217 * 2) ubq daemon gets notified, so wakeup from io_uring_enter(),
218 * then found eventfd is completed, so call ->handle_event()
219 *
220 * 3) inside ->handle_event(), if any io represented by one io
221 * command is completed, ublksrv_complete_io() is called for
222 * this io.
223 *
224 * 4) after returning from ->handle_event(), ubq_daemon will
225 * queue & submit the eventfd io immediately for getting
226 * notification from future event.
227 *
228 * Optional. Only needed if target IO is handled by target its
229 * own pthread context.
230 */
231 void (*handle_event)(const struct ublksrv_queue *);
232
233 /**
234 * One typical use case is to flush meta data, which is usually done
235 * in background. So there isn't any tag from libublksrv for this kind
236 * of IOs, and the target code has to request for allocating extra ios
237 * by passing tgt_type->extra_ios and let this callback consume & handle
238 * these extra IOs.
239 *
240 * nr_queued_io: count of queued IOs in ublksrv_reap_events_uring of
241 * this time
242 *
243 * Optional.
244 */
245 void (*handle_io_background)(const struct ublksrv_queue *, int
246 nr_queued_io);
247
248 /**
249 * show target specific command line for adding new device
250 *
251 * Be careful: this callback is the only one which is not run from
252 * ublk device daemon task context.
253 */
254 void (*usage_for_add)(void);
255
256 /**
257 * initialize this new target, argc/argv includes target specific
258 * command line parameters
259 *
260 * Required.
261 */
262 int (*init_tgt)(struct ublksrv_dev *, int type, int argc,
263 char *argv[]);
264
265 /**
266 * Deinitialize this target
267 *
268 * Optional.
269 */
270 void (*deinit_tgt)(const struct ublksrv_dev *);
271
272 /**
273 * callback for allocating io buffer
274 *
275 * Optional.
276 */
277 void *(*alloc_io_buf)(const struct ublksrv_queue *q, int tag, int size);
278 /**
279 * callback for freeing io buffer
280 *
281 * Optional.
282 */
283 void (*free_io_buf)(const struct ublksrv_queue *q, void *buf, int tag);
284
285 /**
286 * Called when the ublksrv io_uring is idle.
287 *
288 * Optional.
289 */
290 void (*idle_fn)(const struct ublksrv_queue *q, bool enter);
291
292 /** target type */
293 int type;
294
295 /** flags required for ublk driver */
296 unsigned ublk_flags;
297
298 /** flags required for ublksrv */
299 unsigned ublksrv_flags;
300 unsigned pad;
301
302 /** target name */
303 const char *name;
304
305 /**
306 * recovery callback for this target
307 *
308 * Required.
309 */
310 int (*recovery_tgt)(struct ublksrv_dev *, int type);
311
312 /**
313 * queue_data_ptr points to address of q->priviate_data, so that
314 * we still can pass 'const struct ublksrv_queue *', meantime
315 * queue data can be stored to q->private_data via queue_data_ptr.
316 *
317 * ->init_queue provides one chance to override/init the passed
318 * "queue_data" to ublksrv_queue_init(), "queue_data" is set to
319 * q->private_data before calling ->init_queue()
320 */
321 int (*init_queue)(const struct ublksrv_queue *, void **queue_data_ptr);
322
323 /** deinit queue data, counter pair of ->init_queue */
324 void (*deinit_queue)(const struct ublksrv_queue *);
325
326 unsigned long reserved[5];
327 };
328
329 /**
330 * Build sqe->user_data.
331 *
332 * io_uring relies on ->user_data to map cqe to the submitted io represented by
333 * sqe, encodes ublk interested info into ->user_data for handling IO
334 * completion efficiently.
335 *
336 * @param tag ublk io tag
337 * @param op operation code of submitted io
338 * @param tgt_data target data for this io
339 * @param is_taget_io is this one target io, and it should be true for target,
340 * and false for ublksrv built uring command, which is for communicating
341 * with ublk_drv
342 */
build_user_data(unsigned tag,unsigned op,unsigned tgt_data,unsigned is_target_io)343 static inline __u64 build_user_data(unsigned tag, unsigned op,
344 unsigned tgt_data, unsigned is_target_io)
345 {
346 assert(!(tag >> 16) && !(op >> 8) && !(tgt_data >> 16));
347
348 return tag | (op << 16) | (tgt_data << 24) | (__u64)is_target_io << 63;
349 }
350
user_data_to_tag(__u64 user_data)351 static inline unsigned int user_data_to_tag(__u64 user_data)
352 {
353 return user_data & 0xffff;
354 }
355
user_data_to_op(__u64 user_data)356 static inline unsigned int user_data_to_op(__u64 user_data)
357 {
358 return (user_data >> 16) & 0xff;
359 }
360
user_data_to_tgt_data(__u64 user_data)361 static inline unsigned int user_data_to_tgt_data(__u64 user_data)
362 {
363 return (user_data >> 24) & 0xffff;
364 }
365
ublk_pos(__u16 q_id,__u16 tag,__u32 offset)366 static inline __u64 ublk_pos(__u16 q_id, __u16 tag, __u32 offset)
367 {
368 assert(!(offset & ~UBLK_IO_BUF_BITS_MASK));
369
370 return UBLKSRV_IO_BUF_OFFSET +
371 ((((__u64)q_id) << UBLK_QID_OFF) |
372 (((__u64)tag) << UBLK_TAG_OFF) | (__u64)offset);
373 }
374
375 /**
376 * \defgroup ctrl_dev control device API
377 *
378 * Most of APIs are for sending command to ublk control device(/dev/ublk-control),
379 * and some of them are just for device management purpose, such as, retrieving
380 * device json buffer, run_dir, prepare for recovering, get cached device info ...
381 *
382 * Almost all these APIs can be called in random context by random io uring
383 * context
384 *
385 * @{
386 */
387
388 /**
389 * Deinit one control device
390 *
391 * @param dev the ublksrv control device instance
392 *
393 */
394 extern void ublksrv_ctrl_deinit(struct ublksrv_ctrl_dev *dev);
395
396 /**
397 * Allocate and init one control device
398 *
399 * @param data data for allocating & initializing this control device
400 *
401 */
402 extern struct ublksrv_ctrl_dev *ublksrv_ctrl_init(struct ublksrv_dev_data *data);
403
404 /**
405 * Retrieve and store each queue's cpu affinity info into private data of the
406 * control device by sending commands to ublk control device
407 *
408 * @param ctrl_dev the ublksrv control device instance
409 *
410 */
411 extern int ublksrv_ctrl_get_affinity(struct ublksrv_ctrl_dev *ctrl_dev);
412
413 /**
414 * Add one ublk device by sending command to ublk driver
415 *
416 * @param dev the ublksrv control device instance
417 */
418 extern int ublksrv_ctrl_add_dev(struct ublksrv_ctrl_dev *dev);
419
420 /**
421 * Delete this ublk device by sending command to ublk driver
422 *
423 * @param dev the ublksrv control device instance
424 */
425 extern int ublksrv_ctrl_del_dev(struct ublksrv_ctrl_dev *dev);
426
427 /**
428 * Delete this ublk device asynchronously by sending command to ublk driver
429 *
430 * @param dev the ublksrv control device instance
431 */
432 extern int ublksrv_ctrl_del_dev_async(struct ublksrv_ctrl_dev *dev);
433
434 /**
435 * Retrieve ublk device info by sending command to ublk control device
436 *
437 * @param dev the ublksrv control device instance
438 */
439 extern int ublksrv_ctrl_get_info(struct ublksrv_ctrl_dev *dev);
440
441 /**
442 * Stop the specified ublk device by sending command to ublk control device
443 *
444 * @param dev the ublksrv control device instance
445 */
446 extern int ublksrv_ctrl_stop_dev(struct ublksrv_ctrl_dev *dev);
447
448 /**
449 * Dump this ublk device
450 *
451 * @param dev the ublksrv control device instance
452 * @param buf ublk device json buffer, optional
453 */
454 extern void ublksrv_ctrl_dump(struct ublksrv_ctrl_dev *dev, const char *buf);
455
456 /**
457 * Start this ublk device by sending command to ublk control device
458 *
459 * @param ctrl_dev the ublksrv control device instance
460 * @param daemon_pid pid of the ublksrv process
461 */
462 extern int ublksrv_ctrl_start_dev(struct ublksrv_ctrl_dev *ctrl_dev,
463 int daemon_pid);
464
465 /**
466 * Set specified device parameter by sending command to ublk control device
467 *
468 * @param dev the ublksrv control device instance
469 * @param params the specified parameter for setting device
470 */
471 extern int ublksrv_ctrl_set_params(struct ublksrv_ctrl_dev *dev,
472 struct ublk_params *params);
473
474 /**
475 * Get specified device parameter by sending command to ublk control device
476 *
477 * @param dev the ublksrv control device instance
478 * @param params the parameter buffer for storing the device parameter
479 */
480 extern int ublksrv_ctrl_get_params(struct ublksrv_ctrl_dev *dev,
481 struct ublk_params *params);
482
483 /**
484 * Start to recovery device by sending command to ublk control device
485 *
486 * @param dev the ublksrv control device instance
487 */
488 extern int ublksrv_ctrl_start_recovery(struct ublksrv_ctrl_dev *dev);
489
490 /**
491 * End recovery device by sending command to ublk control device
492 *
493 * Once this command is successful, the device is recovered to normal state
494 *
495 * @param dev the ublksrv control device instance
496 * @param daemon_pid pid of the new ublksrv process
497 */
498 extern int ublksrv_ctrl_end_recovery(struct ublksrv_ctrl_dev *dev,
499 int daemon_pid);
500
501 /**
502 * Return cached device info for this device
503 *
504 * @param dev the ublksrv control device instance
505 */
506 extern const struct ublksrv_ctrl_dev_info *ublksrv_ctrl_get_dev_info(
507 const struct ublksrv_ctrl_dev *dev);
508
509 /**
510 * Return feature set supported by ublk driver
511 *
512 * @features points to buffer for holding the returned features
513 */
514 extern int ublksrv_ctrl_get_features(struct ublksrv_ctrl_dev *dev,
515 __u64 *features);
516
517 /**
518 * Return run dir of ublk device
519 *
520 * Device pid file and json string stored under this dir
521 *
522 * @param dev the ublksrv control device instance
523 */
524 extern const char *ublksrv_ctrl_get_run_dir(const struct ublksrv_ctrl_dev *dev);
525
526 /**
527 * Prepare for starting to recovery device
528 *
529 * Setup target type, run_dir and json buffer before starting to recovery device.
530 *
531 * @param dev the ublksrv control device instance
532 * @param tgt_type target type name of this device
533 * @param tgt_ops target type of this devie
534 * @param recovery_jbuf points to device json buffer
535 */
536 extern void ublksrv_ctrl_prep_recovery(struct ublksrv_ctrl_dev *dev,
537 const char *tgt_type, const struct ublksrv_tgt_type *tgt_ops,
538 const char *recovery_jbuf);
539
540 /**
541 * Return device's json buffer
542 *
543 * Setup target type, run_dir and json buffer before starting to recovery device.
544 *
545 * @param dev the ublksrv control device instance
546 */
547 extern const char *ublksrv_ctrl_get_recovery_jbuf(const struct ublksrv_ctrl_dev *dev);
548
549 /**
550 * Return true if this control device is for recovering
551 *
552 * @param dev the ublksrv control device instance
553 */
554 extern bool ublksrv_is_recovering(const struct ublksrv_ctrl_dev *ctrl_dev);
555
556 /** @} */ // end of ctrl_dev group
557
558
559 /**
560 * \defgroup ublksrv_dev ublksrv device API
561 *
562 * ublksrv device ("/dev/ublkcN") level APIs, and ublksrv device focuses on
563 * IO handling related function
564 *
565 * All APIs in this group should be called in ublksrv daemon process context
566 *
567 * @{
568 */
569
570 /**
571 * Allocate and initialize ublksrv device
572 *
573 * @param ctrl_dev the ublksrv control device instance
574 */
575 extern const struct ublksrv_dev *ublksrv_dev_init(const struct ublksrv_ctrl_dev *
576 ctrl_dev);
577
578 /**
579 * Deinitialize and free ublksrv device
580 *
581 * @param dev the ublksrv device instance
582 */
583 extern void ublksrv_dev_deinit(const struct ublksrv_dev *dev);
584
585 /**
586 * Return the associated ublksrv control device instance
587 *
588 * @param dev the ublksrv device instance
589 */
590 extern const struct ublksrv_ctrl_dev *ublksrv_get_ctrl_dev(
591 const struct ublksrv_dev *dev);
592
593 /**
594 * Return pid file FD of this ublksrv device
595 *
596 * @param dev the ublksrv device instance
597 */
598 extern int ublksrv_get_pidfile_fd(const struct ublksrv_dev *dev);
599
600 /**
601 * Set completion queue depth of this ublksrv device
602 *
603 * @param dev the ublksrv device instance
604 * @param cq_depth depth of the completion queue of io_uring
605 */
606 extern void ublksrv_dev_set_cq_depth(struct ublksrv_dev *dev, int cq_depth);
607
608 /**
609 * Get completion queue depth of this ublksrv device
610 *
611 * @param dev the ublksrv device instance
612 */
613 extern int ublksrv_dev_get_cq_depth(struct ublksrv_dev *dev);
614
615 /**
616 *
617 * Apply OOM porotection
618 */
619 extern void ublksrv_apply_oom_protection(void);
620
621 /** @} */ // end of ublksrv_dev group
622
623 /* target json has to include the following key/value */
624 #define UBLKSRV_TGT_NAME_MAX_LEN 32
625 struct ublksrv_tgt_base_json {
626 char name[UBLKSRV_TGT_NAME_MAX_LEN];
627 int type;
628 unsigned int pad;
629 unsigned long long dev_size;
630 unsigned long reserved[8];
631 };
632
633 /**
634 * \defgroup ublksrv_json ublksrv json string API
635 *
636 * ublksrv json string APIs
637 *
638 * APIs for serializing/deserializing device data to/from json string
639 *
640 * @{
641 */
642
643 /**
644 * Serialize json buffer from device's ublksrv_ctrl_dev_info data
645 *
646 * @param dev the ublksrv control device instance
647 * @param buf json buffer
648 * @param len length of json buffer
649 */
650 extern int ublksrv_json_write_dev_info(const struct ublksrv_ctrl_dev *dev,
651 char *buf, int len);
652
653 /**
654 * Deserialize json buffer to ublksrv_ctrl_dev_info instance
655 *
656 * @param json_buf json buffer
657 * @param info device info for storing the parsed ublksrv_ctrl_dev_info
658 */
659 extern int ublksrv_json_read_dev_info(const char *json_buf,
660 struct ublksrv_ctrl_dev_info *info);
661
662 /**
663 * Serialize json buffer from ublksrv queue
664 *
665 * @param dev the ublksrv control device instance
666 * @param jbuf json buffer
667 * @param len length of json buffer
668 * @param qid queue id
669 * @param ubq_daemon_tid queue pthread tid
670 */
671 extern int ublksrv_json_write_queue_info(const struct ublksrv_ctrl_dev *dev,
672 char *jbuf, int len, int qid, int ubq_daemon_tid);
673
674 /**
675 * Deserialize json buffer to ublksrv queue
676 *
677 * @param jbuf json buffer
678 * @param qid queue id
679 * @param tid queue pthread tid
680 * @param affinity_buf queue affinity buffer
681 * @param len length of json buffer
682 */
683 extern int ublksrv_json_read_queue_info(const char *jbuf, int qid,
684 unsigned *tid, char *affinity_buf, int len);
685
686 /**
687 * Deserialize json buffer to target data
688 *
689 * @param jbuf json buffer
690 * @param tgt_buf target buffer
691 * @param len length of json buffer
692 */
693 extern int ublksrv_json_read_target_info(const char *jbuf, char *tgt_buf,
694 int len);
695
696 /**
697 * Deserialize json buffer to target string field
698 *
699 * @param jbuf json buffer
700 * @param len length of json buffer
701 * @param name string name
702 * @param val string value
703 */
704 extern int ublksrv_json_read_target_str_info(const char *jbuf, int len,
705 const char *name, char *val);
706
707 /**
708 * Deserialize json buffer to target ulong field
709 *
710 * @param jbuf json buffer
711 * @param name field name with ulong type
712 * @param val field value with ulong type
713 */
714 extern int ublksrv_json_read_target_ulong_info(const char *jbuf,
715 const char *name, long *val);
716
717 /**
718 * Serialize json buffer from target field with string type
719 *
720 * @param jbuf json buffer
721 * @param len length of json buffer
722 * @param name field name with string type
723 * @param val field value with string type
724 */
725 extern int ublksrv_json_write_target_str_info(char *jbuf, int len,
726 const char *name, const char *val);
727
728 extern int ublksrv_json_write_target_long_info(char *jbuf, int len,
729 const char *name, long val);
730
731 /**
732 * Serialize json buffer from target field with ulong type
733 *
734 * @param jbuf json buffer
735 * @param len length of json buffer
736 * @param name field name with ulong type
737 * @param val field value with ulong type
738 */
739 extern int ublksrv_json_write_target_ulong_info(char *jbuf, int len,
740 const char *name, unsigned long val);
741
742 extern void ublksrv_json_dump(const char *jbuf);
743
744 /**
745 * Deserialize json buffer to ublksrv_tgt_base_json instance
746 *
747 * @param jbuf json buffer
748 * @param tgt ublksrv_tgt_base_json instance
749 */
750 extern int ublksrv_json_read_target_base_info(const char *jbuf,
751 struct ublksrv_tgt_base_json *tgt);
752
753 /**
754 * Serialize json buffer from ublksrv_tgt_base_json
755 *
756 * @param jbuf json buffer
757 * @param len length of json buffer
758 * @param tgt ublksrv_tgt_base_json instance
759 */
760 extern int ublksrv_json_write_target_base_info(char *jbuf, int len,
761 const struct ublksrv_tgt_base_json *tgt);
762
763 /**
764 * Deserialize json buffer to ublk_params instance
765 *
766 * @param p ublk_params instance
767 * @param jbuf json buffer
768 */
769 extern int ublksrv_json_read_params(struct ublk_params *p,
770 const char *jbuf);
771
772 /**
773 * Serialize json buffer from ublk_params instance
774 *
775 * @param p ublk_params instance
776 * @param jbuf json buffer
777 * @param len length of json buffer
778 */
779 extern int ublksrv_json_write_params(const struct ublk_params *p,
780 char *jbuf, int len);
781 extern int ublksrv_json_dump_params(const char *jbuf);
782
783 /**
784 * Return actual length of the json buffer
785 *
786 * @param jbuf json buffer
787 */
788 extern int ublksrv_json_get_length(const char *jbuf);
789
790 /** @} */ // end of ublksrv_json group
791
792 /**
793 * \defgroup ublksrv_queue ublksrv queue API
794 *
795 * ublksrv queue level APIs
796 *
797 * All APIs in this group is supposed to be called in the queue context
798 *
799 * @{
800 */
801
802 /**
803 * Return the specified io private data
804 *
805 * Each IO has unique tag, so we use tag to represent specified io.
806 *
807 * Inside ->init_tgt() callback, target code sets io private data
808 * size via dev->tgt.io_data_size, then io private data will be allocated
809 * in ublksrv_queue_init(). The allocated io private data is very useful
810 * to store target specific io data, then runtime memory allocation in io
811 * handling code path can be avoided.
812 *
813 * @param q the ublksrv queue instance
814 * @param tag tag for this io
815 */
816 extern void *ublksrv_io_private_data(const struct ublksrv_queue *q, int tag);
817
818 /**
819 * Return the specified io generic io data
820 *
821 * Each IO has unique tag, so we use tag to represent specified io.
822 *
823 * @param q the ublksrv queue instance
824 * @param tag tag for this io
825 * @return 'struct ublk_io_data' instance, which is for storing io descriptor,
826 * tag, and private data
827 */
828 extern const struct ublk_io_data *ublksrv_queue_get_io_data(
829 const struct ublksrv_queue *q, int tag);
830
831 /**
832 * Return pre-allocated io buffer
833 *
834 * Each IO has unique tag, so we use tag to represent specified io.
835 *
836 * @param q the ublksrv queue instance
837 * @param tag tag for this io
838 * @return pre-allocated io buffer for this io
839 */
840 extern void *ublksrv_queue_get_io_buf(const struct ublksrv_queue *q, int tag);
841
842 /**
843 * Return current queue state
844 *
845 * queue state is usually for debug purpose
846 *
847 * @param q the ublksrv queue instance
848 * @return queue current state
849 */
850 extern unsigned int ublksrv_queue_state(const struct ublksrv_queue *q);
851
852 /**
853 * Allocate and initialize ublksrv queue instance
854 *
855 * @param dev the ublksrv device instance
856 * @param q_id queue id
857 * @param queue_data queue private data
858 */
859 extern const struct ublksrv_queue *ublksrv_queue_init(const struct ublksrv_dev *dev,
860 unsigned short q_id, void *queue_data);
861
862 /**
863 * Deinit & free ublksrv queue instance
864 *
865 * @param q the ublksrv queue instance
866 */
867 extern void ublksrv_queue_deinit(const struct ublksrv_queue *q);
868
869 /**
870 * Return how many unconsumed cqes in CQ of queue uring
871 *
872 * @param q the ublksrv queue instance
873 *
874 * Return -1 if uring isn't setup correctly
875 */
876 extern int ublksrv_queue_unconsumed_cqes(const struct ublksrv_queue *q);
877
878 extern int ublksrv_queue_handled_event(const struct ublksrv_queue *q);
879 extern int ublksrv_queue_send_event(const struct ublksrv_queue *q);
880
881 /**
882 * Return the specified queue instance by ublksrv device and qid
883 *
884 * Retrieve queue instance by ublksrv device and queue id
885 *
886 * @param dev the ublksrv device instance
887 * @param q_id queue id
888 */
889 extern const struct ublksrv_queue *ublksrv_get_queue(const struct ublksrv_dev *dev,
890 int q_id);
891
892 /**
893 * Process target IO & IO command from this queue's io_uring
894 *
895 * Handle incoming io command by calling target ->handle_io_async(), or
896 * call ->tgt_io_done() if target IO is completed.
897 *
898 * It is the engine of libulksrv, almost everything is driven by this
899 * API.
900 *
901 * @param q the ublksrv queue instance
902 */
903 extern int ublksrv_process_io(const struct ublksrv_queue *q);
904
905 /**
906 * Complete specified io with result of 'res'
907 *
908 * This API will tell ublk driver via /dev/ublkcN that this IO is completed.
909 *
910 * @param q the ublksrv queue instance
911 * @param tag the io to be completed
912 * @param res io result
913 */
914 extern int ublksrv_complete_io(const struct ublksrv_queue *q, unsigned tag, int res);
915 /** @} */ // end of ublksrv_queue group
916
917 #ifdef __cplusplus
918 }
919 #endif
920 #endif
921