xref: /dpdk/lib/vhost/rte_vhost.h (revision d8381a8f54cdc789c4260efefb5a17b9612f417e)
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(c) 2010-2017 Intel Corporation
3  */
4 
5 #ifndef _RTE_VHOST_H_
6 #define _RTE_VHOST_H_
7 
8 /**
9  * @file
10  * Interface to vhost-user
11  */
12 
13 #include <stdbool.h>
14 #include <stdint.h>
15 #include <sys/eventfd.h>
16 
17 #include <rte_compat.h>
18 #include <rte_memory.h>
19 #include <rte_mempool.h>
20 
21 #ifndef __cplusplus
22 /* These are not C++-aware. */
23 #include <linux/vhost.h>
24 #include <linux/virtio_ring.h>
25 #include <linux/virtio_net.h>
26 #endif
27 
28 #ifdef __cplusplus
29 extern "C" {
30 #endif
31 
32 #define RTE_VHOST_USER_CLIENT		(1ULL << 0)
33 #define RTE_VHOST_USER_NO_RECONNECT	(1ULL << 1)
34 #define RTE_VHOST_USER_RESERVED_1	(1ULL << 2)
35 #define RTE_VHOST_USER_IOMMU_SUPPORT	(1ULL << 3)
36 #define RTE_VHOST_USER_POSTCOPY_SUPPORT		(1ULL << 4)
37 /* support mbuf with external buffer attached */
38 #define RTE_VHOST_USER_EXTBUF_SUPPORT	(1ULL << 5)
39 /* support only linear buffers (no chained mbufs) */
40 #define RTE_VHOST_USER_LINEARBUF_SUPPORT	(1ULL << 6)
41 #define RTE_VHOST_USER_ASYNC_COPY	(1ULL << 7)
42 #define RTE_VHOST_USER_NET_COMPLIANT_OL_FLAGS	(1ULL << 8)
43 #define RTE_VHOST_USER_NET_STATS_ENABLE	(1ULL << 9)
44 #define RTE_VHOST_USER_ASYNC_CONNECT	(1ULL << 10)
45 
46 /* Features. */
47 #ifndef VIRTIO_NET_F_GUEST_ANNOUNCE
48  #define VIRTIO_NET_F_GUEST_ANNOUNCE 21
49 #endif
50 
51 #ifndef VIRTIO_NET_F_MQ
52  #define VIRTIO_NET_F_MQ		22
53 #endif
54 
55 #ifndef VIRTIO_NET_F_MTU
56  #define VIRTIO_NET_F_MTU 3
57 #endif
58 
59 #ifndef VIRTIO_F_ANY_LAYOUT
60  #define VIRTIO_F_ANY_LAYOUT		27
61 #endif
62 
63 /** Protocol features. */
64 #ifndef VHOST_USER_PROTOCOL_F_MQ
65 #define VHOST_USER_PROTOCOL_F_MQ	0
66 #endif
67 
68 #ifndef VHOST_USER_PROTOCOL_F_LOG_SHMFD
69 #define VHOST_USER_PROTOCOL_F_LOG_SHMFD	1
70 #endif
71 
72 #ifndef VHOST_USER_PROTOCOL_F_RARP
73 #define VHOST_USER_PROTOCOL_F_RARP	2
74 #endif
75 
76 #ifndef VHOST_USER_PROTOCOL_F_REPLY_ACK
77 #define VHOST_USER_PROTOCOL_F_REPLY_ACK	3
78 #endif
79 
80 #ifndef VHOST_USER_PROTOCOL_F_NET_MTU
81 #define VHOST_USER_PROTOCOL_F_NET_MTU	4
82 #endif
83 
84 #ifndef VHOST_USER_PROTOCOL_F_BACKEND_REQ
85 #define VHOST_USER_PROTOCOL_F_BACKEND_REQ	5
86 #endif
87 
88 #ifndef VHOST_USER_PROTOCOL_F_CRYPTO_SESSION
89 #define VHOST_USER_PROTOCOL_F_CRYPTO_SESSION 7
90 #endif
91 
92 #ifndef VHOST_USER_PROTOCOL_F_PAGEFAULT
93 #define VHOST_USER_PROTOCOL_F_PAGEFAULT 8
94 #endif
95 
96 #ifndef VHOST_USER_PROTOCOL_F_CONFIG
97 #define VHOST_USER_PROTOCOL_F_CONFIG 9
98 #endif
99 
100 #ifndef VHOST_USER_PROTOCOL_F_BACKEND_SEND_FD
101 #define VHOST_USER_PROTOCOL_F_BACKEND_SEND_FD 10
102 #endif
103 
104 #ifndef VHOST_USER_PROTOCOL_F_HOST_NOTIFIER
105 #define VHOST_USER_PROTOCOL_F_HOST_NOTIFIER 11
106 #endif
107 
108 #ifndef VHOST_USER_PROTOCOL_F_INFLIGHT_SHMFD
109 #define VHOST_USER_PROTOCOL_F_INFLIGHT_SHMFD 12
110 #endif
111 
112 #ifndef VHOST_USER_PROTOCOL_F_STATUS
113 #define VHOST_USER_PROTOCOL_F_STATUS 16
114 #endif
115 
116 /** Indicate whether protocol features negotiation is supported. */
117 #ifndef VHOST_USER_F_PROTOCOL_FEATURES
118 #define VHOST_USER_F_PROTOCOL_FEATURES	30
119 #endif
120 
121 #define RTE_MAX_VHOST_DEVICE	1024
122 
123 #define RTE_VHOST_VDPA_DEVICE_TYPE_NET 0
124 #define RTE_VHOST_VDPA_DEVICE_TYPE_BLK 1
125 
126 struct rte_vdpa_device;
127 
128 /**
129  * Information relating to memory regions including offsets to
130  * addresses in QEMUs memory file.
131  */
132 struct rte_vhost_mem_region {
133 	uint64_t guest_phys_addr;
134 	uint64_t guest_user_addr;
135 	uint64_t host_user_addr;
136 	uint64_t size;
137 	void	 *mmap_addr;
138 	uint64_t mmap_size;
139 	int fd;
140 };
141 
142 /**
143  * Memory structure includes region and mapping information.
144  */
145 struct rte_vhost_memory {
146 	uint32_t nregions;
147 	struct rte_vhost_mem_region regions[];
148 };
149 
150 struct rte_vhost_inflight_desc_split {
151 	uint8_t inflight;
152 	uint8_t padding[5];
153 	uint16_t next;
154 	uint64_t counter;
155 };
156 
157 struct rte_vhost_inflight_info_split {
158 	uint64_t features;
159 	uint16_t version;
160 	uint16_t desc_num;
161 	uint16_t last_inflight_io;
162 	uint16_t used_idx;
163 	struct rte_vhost_inflight_desc_split desc[];
164 };
165 
166 struct rte_vhost_inflight_desc_packed {
167 	uint8_t inflight;
168 	uint8_t padding;
169 	uint16_t next;
170 	uint16_t last;
171 	uint16_t num;
172 	uint64_t counter;
173 	uint16_t id;
174 	uint16_t flags;
175 	uint32_t len;
176 	uint64_t addr;
177 };
178 
179 struct rte_vhost_inflight_info_packed {
180 	uint64_t features;
181 	uint16_t version;
182 	uint16_t desc_num;
183 	uint16_t free_head;
184 	uint16_t old_free_head;
185 	uint16_t used_idx;
186 	uint16_t old_used_idx;
187 	uint8_t used_wrap_counter;
188 	uint8_t old_used_wrap_counter;
189 	uint8_t padding[7];
190 	struct rte_vhost_inflight_desc_packed desc[];
191 };
192 
193 struct rte_vhost_resubmit_desc {
194 	uint16_t index;
195 	uint64_t counter;
196 };
197 
198 struct rte_vhost_resubmit_info {
199 	struct rte_vhost_resubmit_desc *resubmit_list;
200 	uint16_t resubmit_num;
201 };
202 
203 struct rte_vhost_ring_inflight {
204 	union {
205 		struct rte_vhost_inflight_info_split *inflight_split;
206 		struct rte_vhost_inflight_info_packed *inflight_packed;
207 	};
208 
209 	struct rte_vhost_resubmit_info *resubmit_inflight;
210 };
211 
212 struct rte_vhost_vring {
213 	union {
214 		struct vring_desc *desc;
215 		struct vring_packed_desc *desc_packed;
216 	};
217 	union {
218 		struct vring_avail *avail;
219 		struct vring_packed_desc_event *driver_event;
220 	};
221 	union {
222 		struct vring_used *used;
223 		struct vring_packed_desc_event *device_event;
224 	};
225 	uint64_t		log_guest_addr;
226 
227 	/** Deprecated, use rte_vhost_vring_call() instead. */
228 	int			callfd;
229 
230 	int			kickfd;
231 	uint16_t		size;
232 };
233 
234 /**
235  * Possible results of the vhost user message handling callbacks
236  */
237 enum rte_vhost_msg_result {
238 	/* Message handling failed */
239 	RTE_VHOST_MSG_RESULT_ERR = -1,
240 	/* Message handling successful */
241 	RTE_VHOST_MSG_RESULT_OK =  0,
242 	/* Message handling successful and reply prepared */
243 	RTE_VHOST_MSG_RESULT_REPLY =  1,
244 	/* Message not handled */
245 	RTE_VHOST_MSG_RESULT_NOT_HANDLED,
246 };
247 
248 /**
249  * Function prototype for the vhost backend to handle specific vhost user
250  * messages.
251  *
252  * @param vid
253  *  vhost device id
254  * @param msg
255  *  Message pointer.
256  * @return
257  *  RTE_VHOST_MSG_RESULT_OK on success,
258  *  RTE_VHOST_MSG_RESULT_REPLY on success with reply,
259  *  RTE_VHOST_MSG_RESULT_ERR on failure,
260  *  RTE_VHOST_MSG_RESULT_NOT_HANDLED if message was not handled.
261  */
262 typedef enum rte_vhost_msg_result (*rte_vhost_msg_handle)(int vid, void *msg);
263 
264 /**
265  * Optional vhost user message handlers.
266  */
267 struct rte_vhost_user_extern_ops {
268 	/* Called prior to the frontend message handling. */
269 	rte_vhost_msg_handle pre_msg_handle;
270 	/* Called after the frontend message handling. */
271 	rte_vhost_msg_handle post_msg_handle;
272 };
273 
274 /**
275  * Device and vring operations.
276  */
277 struct rte_vhost_device_ops {
278 	int (*new_device)(int vid);		/**< Add device. */
279 	void (*destroy_device)(int vid);	/**< Remove device. */
280 
281 	int (*vring_state_changed)(int vid, uint16_t queue_id, int enable);	/**< triggered when a vring is enabled or disabled */
282 
283 	/**
284 	 * Features could be changed after the feature negotiation.
285 	 * For example, VHOST_F_LOG_ALL will be set/cleared at the
286 	 * start/end of live migration, respectively. This callback
287 	 * is used to inform the application on such change.
288 	 */
289 	int (*features_changed)(int vid, uint64_t features);
290 
291 	int (*new_connection)(int vid);
292 	void (*destroy_connection)(int vid);
293 
294 	/**
295 	 * This callback gets called each time a guest gets notified
296 	 * about waiting packets. This is the interrupt handling through
297 	 * the eventfd_write(callfd), which can be used for counting these
298 	 * "slow" syscalls.
299 	 */
300 	void (*guest_notified)(int vid);
301 
302 	/**
303 	 * If this callback is registered, notification to the guest can
304 	 * be handled by the front-end calling rte_vhost_notify_guest().
305 	 * If it's not handled, 'false' should be returned. This can be used
306 	 * to remove the "slow" eventfd_write() syscall from the datapath.
307 	 */
308 	bool (*guest_notify)(int vid, uint16_t queue_id);
309 };
310 
311 /**
312  * Power monitor condition.
313  */
314 struct rte_vhost_power_monitor_cond {
315 	/**< Address to monitor for changes */
316 	volatile void *addr;
317 	/**< If the `mask` is non-zero, location pointed
318 	 *   to by `addr` will be read and masked, then
319 	 *   compared with this value.
320 	 */
321 	uint64_t val;
322 	/**< 64-bit mask to extract value read from `addr` */
323 	uint64_t mask;
324 	/**< Data size (in bytes) that will be read from the
325 	 *   monitored memory location (`addr`).
326 	 */
327 	uint8_t size;
328 	/**< If 1, and masked value that read from 'addr' equals
329 	 *   'val', the driver should skip core sleep. If 0, and
330 	 *  masked value that read from 'addr' does not equal 'val',
331 	 *  the driver should skip core sleep.
332 	 */
333 	uint8_t match;
334 };
335 
336 /** Maximum name length for the statistics counters */
337 #define RTE_VHOST_STATS_NAME_SIZE 64
338 
339 /**
340  * Vhost virtqueue statistics structure
341  *
342  * This structure is used by rte_vhost_vring_stats_get() to provide
343  * virtqueue statistics to the calling application.
344  * It maps a name ID, corresponding to an index in the array returned
345  * by rte_vhost_vring_stats_get_names(), to a statistic value.
346  */
347 struct rte_vhost_stat {
348 	uint64_t id;    /**< The index in xstats name array. */
349 	uint64_t value; /**< The statistic counter value. */
350 };
351 
352 /**
353  * Vhost virtqueue statistic name element
354  *
355  * This structure is used by rte_vhost_vring_stats_get_names() to
356  * provide virtqueue statistics names to the calling application.
357  */
358 struct rte_vhost_stat_name {
359 	char name[RTE_VHOST_STATS_NAME_SIZE]; /**< The statistic name. */
360 };
361 
362 /**
363  * Convert guest physical address to host virtual address
364  *
365  * @param mem
366  *  the guest memory regions
367  * @param gpa
368  *  the guest physical address for querying
369  * @param len
370  *  the size of the requested area to map, updated with actual size mapped
371  * @return
372  *  the host virtual address on success, 0 on failure
373  */
374 static __rte_always_inline uint64_t
375 rte_vhost_va_from_guest_pa(struct rte_vhost_memory *mem,
376 						   uint64_t gpa, uint64_t *len)
377 {
378 	struct rte_vhost_mem_region *r;
379 	uint32_t i;
380 
381 	for (i = 0; i < mem->nregions; i++) {
382 		r = &mem->regions[i];
383 		if (gpa >= r->guest_phys_addr &&
384 		    gpa <  r->guest_phys_addr + r->size) {
385 
386 			if (unlikely(*len > r->guest_phys_addr + r->size - gpa))
387 				*len = r->guest_phys_addr + r->size - gpa;
388 
389 			return gpa - r->guest_phys_addr +
390 			       r->host_user_addr;
391 		}
392 	}
393 	*len = 0;
394 
395 	return 0;
396 }
397 
398 #define RTE_VHOST_NEED_LOG(features)	((features) & (1ULL << VHOST_F_LOG_ALL))
399 
400 /**
401  * Log the memory write start with given address.
402  *
403  * This function only need be invoked when the live migration starts.
404  * Therefore, we won't need call it at all in the most of time. For
405  * making the performance impact be minimum, it's suggested to do a
406  * check before calling it:
407  *
408  *        if (unlikely(RTE_VHOST_NEED_LOG(features)))
409  *                rte_vhost_log_write(vid, addr, len);
410  *
411  * @param vid
412  *  vhost device ID
413  * @param addr
414  *  the starting address for write (in guest physical address space)
415  * @param len
416  *  the length to write
417  */
418 void rte_vhost_log_write(int vid, uint64_t addr, uint64_t len);
419 
420 /**
421  * Log the used ring update start at given offset.
422  *
423  * Same as rte_vhost_log_write, it's suggested to do a check before
424  * calling it:
425  *
426  *        if (unlikely(RTE_VHOST_NEED_LOG(features)))
427  *                rte_vhost_log_used_vring(vid, vring_idx, offset, len);
428  *
429  * @param vid
430  *  vhost device ID
431  * @param vring_idx
432  *  the vring index
433  * @param offset
434  *  the offset inside the used ring
435  * @param len
436  *  the length to write
437  */
438 void rte_vhost_log_used_vring(int vid, uint16_t vring_idx,
439 			      uint64_t offset, uint64_t len);
440 
441 int rte_vhost_enable_guest_notification(int vid, uint16_t queue_id, int enable);
442 
443 /**
444  * @warning
445  * @b EXPERIMENTAL: this API may change, or be removed, without prior notice.
446  *
447  * Inject the offloaded interrupt into the vhost device's queue.
448  * @see guest_notify vhost device operation
449  *
450  * @param vid
451  *  vhost device ID
452  * @param queue_id
453  *  virtio queue index
454  */
455 __rte_experimental
456 void rte_vhost_notify_guest(int vid, uint16_t queue_id);
457 
458 /**
459  * Register vhost driver. path could be different for multiple
460  * instance support.
461  */
462 int rte_vhost_driver_register(const char *path, uint64_t flags);
463 
464 /* Unregister vhost driver. This is only meaningful to vhost user. */
465 int rte_vhost_driver_unregister(const char *path);
466 
467 /**
468  * Set the vdpa device id, enforce single connection per socket
469  *
470  * @param path
471  *  The vhost-user socket file path
472  * @param dev
473  *  vDPA device pointer
474  * @return
475  *  0 on success, -1 on failure
476  */
477 int
478 rte_vhost_driver_attach_vdpa_device(const char *path,
479 		struct rte_vdpa_device *dev);
480 
481 /**
482  * Unset the vdpa device id
483  *
484  * @param path
485  *  The vhost-user socket file path
486  * @return
487  *  0 on success, -1 on failure
488  */
489 int
490 rte_vhost_driver_detach_vdpa_device(const char *path);
491 
492 /**
493  * Get the device id
494  *
495  * @param path
496  *  The vhost-user socket file path
497  * @return
498  *  vDPA device pointer, NULL on failure
499  */
500 struct rte_vdpa_device *
501 rte_vhost_driver_get_vdpa_device(const char *path);
502 
503 /**
504  * Get the device type of the vdpa device.
505  *
506  * @param path
507  *  The vhost-user socket file path
508  * @param type
509  *  the device type of the vdpa device
510  * @return
511  *  0 on success, -1 on failure
512  */
513 int
514 rte_vhost_driver_get_vdpa_dev_type(const char *path, uint32_t *type);
515 
516 /**
517  * Set the feature bits the vhost-user driver supports.
518  *
519  * @param path
520  *  The vhost-user socket file path
521  * @param features
522  *  Supported features
523  * @return
524  *  0 on success, -1 on failure
525  */
526 int rte_vhost_driver_set_features(const char *path, uint64_t features);
527 
528 /**
529  * Enable vhost-user driver features.
530  *
531  * Note that
532  * - the param features should be a subset of the feature bits provided
533  *   by rte_vhost_driver_set_features().
534  * - it must be invoked before vhost-user negotiation starts.
535  *
536  * @param path
537  *  The vhost-user socket file path
538  * @param features
539  *  Features to enable
540  * @return
541  *  0 on success, -1 on failure
542  */
543 int rte_vhost_driver_enable_features(const char *path, uint64_t features);
544 
545 /**
546  * Disable vhost-user driver features.
547  *
548  * The two notes at rte_vhost_driver_enable_features() also apply here.
549  *
550  * @param path
551  *  The vhost-user socket file path
552  * @param features
553  *  Features to disable
554  * @return
555  *  0 on success, -1 on failure
556  */
557 int rte_vhost_driver_disable_features(const char *path, uint64_t features);
558 
559 /**
560  * Get the feature bits before feature negotiation.
561  *
562  * @param path
563  *  The vhost-user socket file path
564  * @param features
565  *  A pointer to store the queried feature bits
566  * @return
567  *  0 on success, -1 on failure
568  */
569 int rte_vhost_driver_get_features(const char *path, uint64_t *features);
570 
571 /**
572  * Set the protocol feature bits before feature negotiation.
573  *
574  * @param path
575  *  The vhost-user socket file path
576  * @param protocol_features
577  *  Supported protocol features
578  * @return
579  *  0 on success, -1 on failure
580  */
581 int
582 rte_vhost_driver_set_protocol_features(const char *path,
583 		uint64_t protocol_features);
584 
585 /**
586  * Get the protocol feature bits before feature negotiation.
587  *
588  * @param path
589  *  The vhost-user socket file path
590  * @param protocol_features
591  *  A pointer to store the queried protocol feature bits
592  * @return
593  *  0 on success, -1 on failure
594  */
595 int
596 rte_vhost_driver_get_protocol_features(const char *path,
597 		uint64_t *protocol_features);
598 
599 /**
600  * Get the queue number bits before feature negotiation.
601  *
602  * @param path
603  *  The vhost-user socket file path
604  * @param queue_num
605  *  A pointer to store the queried queue number bits
606  * @return
607  *  0 on success, -1 on failure
608  */
609 int
610 rte_vhost_driver_get_queue_num(const char *path, uint32_t *queue_num);
611 
612 /**
613  * Set the maximum number of queue pairs supported by the device.
614  * The value set is ignored for Vhost-user backends. It is only taken into
615  * account with VDUSE backends.
616  *
617  * @param path
618  *  The vhost-user socket file path
619  * @param max_queue_pairs
620  *  The maximum number of queue pairs
621  * @return
622  *  0 on success, -1 on failure
623  */
624 int
625 rte_vhost_driver_set_max_queue_num(const char *path, uint32_t max_queue_pairs);
626 
627 /**
628  * Get the feature bits after negotiation
629  *
630  * @param vid
631  *  Vhost device ID
632  * @param features
633  *  A pointer to store the queried feature bits
634  * @return
635  *  0 on success, -1 on failure
636  */
637 int rte_vhost_get_negotiated_features(int vid, uint64_t *features);
638 
639 /**
640  * Get the protocol feature bits after negotiation
641  *
642  * @param vid
643  *  Vhost device ID
644  * @param protocol_features
645  *  A pointer to store the queried protocol feature bits
646  * @return
647  *  0 on success, -1 on failure
648  */
649 int
650 rte_vhost_get_negotiated_protocol_features(int vid,
651 					   uint64_t *protocol_features);
652 
653 /* Register callbacks. */
654 int rte_vhost_driver_callback_register(const char *path,
655 	struct rte_vhost_device_ops const * const ops);
656 
657 /**
658  *
659  * Start the vhost-user driver.
660  *
661  * This function triggers the vhost-user negotiation.
662  *
663  * @param path
664  *  The vhost-user socket file path
665  * @return
666  *  0 on success, -1 on failure
667  */
668 int rte_vhost_driver_start(const char *path);
669 
670 /**
671  * Get the MTU value of the device if set in QEMU.
672  *
673  * @param vid
674  *  virtio-net device ID
675  * @param mtu
676  *  The variable to store the MTU value
677  *
678  * @return
679  *  0: success
680  *  -EAGAIN: device not yet started
681  *  -ENOTSUP: device does not support MTU feature
682  */
683 int rte_vhost_get_mtu(int vid, uint16_t *mtu);
684 
685 /**
686  * Get the numa node from which the virtio net device's memory
687  * is allocated.
688  *
689  * @param vid
690  *  vhost device ID
691  *
692  * @return
693  *  The numa node, -1 on failure
694  */
695 int rte_vhost_get_numa_node(int vid);
696 
697 /**
698  * Get the number of vrings the device supports.
699  *
700  * @param vid
701  *  vhost device ID
702  *
703  * @return
704  *  The number of vrings, 0 on failure
705  */
706 uint16_t rte_vhost_get_vring_num(int vid);
707 
708 /**
709  * Get the virtio net device's ifname, which is the vhost-user socket
710  * file path.
711  *
712  * @param vid
713  *  vhost device ID
714  * @param buf
715  *  The buffer to stored the queried ifname
716  * @param len
717  *  The length of buf
718  *
719  * @return
720  *  0 on success, -1 on failure
721  */
722 int rte_vhost_get_ifname(int vid, char *buf, size_t len);
723 
724 /**
725  * Get how many avail entries are left in the queue
726  *
727  * @param vid
728  *  vhost device ID
729  * @param queue_id
730  *  virtio queue index
731  *
732  * @return
733  *  num of avail entries left
734  */
735 uint16_t rte_vhost_avail_entries(int vid, uint16_t queue_id);
736 
737 struct rte_mbuf;
738 struct rte_mempool;
739 /**
740  * This function adds buffers to the virtio devices RX virtqueue. Buffers can
741  * be received from the physical port or from another virtual device. A packet
742  * count is returned to indicate the number of packets that were successfully
743  * added to the RX queue.
744  * @param vid
745  *  vhost device ID
746  * @param queue_id
747  *  virtio queue index in mq case
748  * @param pkts
749  *  array to contain packets to be enqueued
750  * @param count
751  *  packets num to be enqueued
752  * @return
753  *  num of packets enqueued
754  */
755 uint16_t rte_vhost_enqueue_burst(int vid, uint16_t queue_id,
756 	struct rte_mbuf **pkts, uint16_t count);
757 
758 /**
759  * This function gets guest buffers from the virtio device TX virtqueue,
760  * construct host mbufs, copies guest buffer content to host mbufs and
761  * store them in pkts to be processed.
762  * @param vid
763  *  vhost device ID
764  * @param queue_id
765  *  virtio queue index in mq case
766  * @param mbuf_pool
767  *  mbuf_pool where host mbuf is allocated.
768  * @param pkts
769  *  array to contain packets to be dequeued
770  * @param count
771  *  packets num to be dequeued
772  * @return
773  *  num of packets dequeued
774  */
775 uint16_t rte_vhost_dequeue_burst(int vid, uint16_t queue_id,
776 	struct rte_mempool *mbuf_pool, struct rte_mbuf **pkts, uint16_t count);
777 
778 /**
779  * Get guest mem table: a list of memory regions.
780  *
781  * An rte_vhost_vhost_memory object will be allocated internally, to hold the
782  * guest memory regions. Application should free it at destroy_device()
783  * callback.
784  *
785  * @param vid
786  *  vhost device ID
787  * @param mem
788  *  To store the returned mem regions
789  * @return
790  *  0 on success, -1 on failure
791  */
792 int rte_vhost_get_mem_table(int vid, struct rte_vhost_memory **mem);
793 
794 /**
795  * Get guest vring info, including the vring address, vring size, etc.
796  *
797  * @param vid
798  *  vhost device ID
799  * @param vring_idx
800  *  vring index
801  * @param vring
802  *  the structure to hold the requested vring info
803  * @return
804  *  0 on success, -1 on failure
805  */
806 int rte_vhost_get_vhost_vring(int vid, uint16_t vring_idx,
807 			      struct rte_vhost_vring *vring);
808 
809 /**
810  * Get guest inflight vring info, including inflight ring and resubmit list.
811  *
812  * @param vid
813  *  vhost device ID
814  * @param vring_idx
815  *  vring index
816  * @param vring
817  *  the structure to hold the requested inflight vring info
818  * @return
819  *  0 on success, -1 on failure
820  */
821 int
822 rte_vhost_get_vhost_ring_inflight(int vid, uint16_t vring_idx,
823 	struct rte_vhost_ring_inflight *vring);
824 
825 /**
826  * Set split inflight descriptor.
827  *
828  * This function save descriptors that has been consumed in available
829  * ring
830  *
831  * @param vid
832  *  vhost device ID
833  * @param vring_idx
834  *  vring index
835  * @param idx
836  *  inflight entry index
837  * @return
838  *  0 on success, -1 on failure
839  */
840 int
841 rte_vhost_set_inflight_desc_split(int vid, uint16_t vring_idx,
842 	uint16_t idx);
843 
844 /**
845  * Set packed inflight descriptor and get corresponding inflight entry
846  *
847  * This function save descriptors that has been consumed
848  *
849  * @param vid
850  *  vhost device ID
851  * @param vring_idx
852  *  vring index
853  * @param head
854  *  head of descriptors
855  * @param last
856  *  last of descriptors
857  * @param inflight_entry
858  *  corresponding inflight entry
859  * @return
860  *  0 on success, -1 on failure
861  */
862 int
863 rte_vhost_set_inflight_desc_packed(int vid, uint16_t vring_idx,
864 	uint16_t head, uint16_t last, uint16_t *inflight_entry);
865 
866 /**
867  * Save the head of list that the last batch of used descriptors.
868  *
869  * @param vid
870  *  vhost device ID
871  * @param vring_idx
872  *  vring index
873  * @param idx
874  *  descriptor entry index
875  * @return
876  *  0 on success, -1 on failure
877  */
878 int
879 rte_vhost_set_last_inflight_io_split(int vid,
880 	uint16_t vring_idx, uint16_t idx);
881 
882 /**
883  * Update the inflight free_head, used_idx and used_wrap_counter.
884  *
885  * This function will update status first before updating descriptors
886  * to used
887  *
888  * @param vid
889  *  vhost device ID
890  * @param vring_idx
891  *  vring index
892  * @param head
893  *  head of descriptors
894  * @return
895  *  0 on success, -1 on failure
896  */
897 int
898 rte_vhost_set_last_inflight_io_packed(int vid,
899 	uint16_t vring_idx, uint16_t head);
900 
901 /**
902  * Clear the split inflight status.
903  *
904  * @param vid
905  *  vhost device ID
906  * @param vring_idx
907  *  vring index
908  * @param last_used_idx
909  *  last used idx of used ring
910  * @param idx
911  *  inflight entry index
912  * @return
913  *  0 on success, -1 on failure
914  */
915 int
916 rte_vhost_clr_inflight_desc_split(int vid, uint16_t vring_idx,
917 	uint16_t last_used_idx, uint16_t idx);
918 
919 /**
920  * Clear the packed inflight status.
921  *
922  * @param vid
923  *  vhost device ID
924  * @param vring_idx
925  *  vring index
926  * @param head
927  *  inflight entry index
928  * @return
929  *  0 on success, -1 on failure
930  */
931 int
932 rte_vhost_clr_inflight_desc_packed(int vid, uint16_t vring_idx,
933 	uint16_t head);
934 
935 /**
936  * Notify the guest that used descriptors have been added to the vring.  This
937  * function acts as a memory barrier.
938  *
939  * @param vid
940  *  vhost device ID
941  * @param vring_idx
942  *  vring index
943  * @return
944  *  0 on success, -1 on failure
945  */
946 int rte_vhost_vring_call(int vid, uint16_t vring_idx);
947 
948 /**
949  * Notify the guest that used descriptors have been added to the vring.  This
950  * function acts as a memory barrier.  This function will return -EAGAIN when
951  * vq's access lock is held by other thread, user should try again later.
952  *
953  * @param vid
954  *  vhost device ID
955  * @param vring_idx
956  *  vring index
957  * @return
958  *  0 on success, -1 on failure, -EAGAIN for another retry
959  */
960 int rte_vhost_vring_call_nonblock(int vid, uint16_t vring_idx);
961 
962 /**
963  * Get vhost RX queue avail count.
964  *
965  * @param vid
966  *  vhost device ID
967  * @param qid
968  *  virtio queue index in mq case
969  * @return
970  *  num of desc available
971  */
972 uint32_t rte_vhost_rx_queue_count(int vid, uint16_t qid);
973 
974 /**
975  * Get power monitor address of the vhost device
976  *
977  * @param vid
978  *  vhost device ID
979  * @param queue_id
980  *  vhost queue ID
981  * @param pmc
982  *  power monitor condition
983  * @return
984  *  0 on success, -1 on failure
985  */
986 int
987 rte_vhost_get_monitor_addr(int vid, uint16_t queue_id,
988 		struct rte_vhost_power_monitor_cond *pmc);
989 
990 /**
991  * Get log base and log size of the vhost device
992  *
993  * @param vid
994  *  vhost device ID
995  * @param log_base
996  *  vhost log base
997  * @param log_size
998  *  vhost log size
999  * @return
1000  *  0 on success, -1 on failure
1001  */
1002 int
1003 rte_vhost_get_log_base(int vid, uint64_t *log_base, uint64_t *log_size);
1004 
1005 /**
1006  * Get last_avail/used_idx of the vhost virtqueue
1007  *
1008  * @param vid
1009  *  vhost device ID
1010  * @param queue_id
1011  *  vhost queue index
1012  * @param last_avail_idx
1013  *  vhost last_avail_idx to get
1014  * @param last_used_idx
1015  *  vhost last_used_idx to get
1016  * @return
1017  *  0 on success, -1 on failure
1018  */
1019 int
1020 rte_vhost_get_vring_base(int vid, uint16_t queue_id,
1021 		uint16_t *last_avail_idx, uint16_t *last_used_idx);
1022 
1023 /**
1024  * Get last_avail/last_used of the vhost virtqueue
1025  *
1026  * This function is designed for the reconnection and it's specific for
1027  * the packed ring as we can get the two parameters from the inflight
1028  * queueregion
1029  *
1030  * @param vid
1031  *  vhost device ID
1032  * @param queue_id
1033  *  vhost queue index
1034  * @param last_avail_idx
1035  *  vhost last_avail_idx to get
1036  * @param last_used_idx
1037  *  vhost last_used_idx to get
1038  * @return
1039  *  0 on success, -1 on failure
1040  */
1041 int
1042 rte_vhost_get_vring_base_from_inflight(int vid,
1043 	uint16_t queue_id, uint16_t *last_avail_idx, uint16_t *last_used_idx);
1044 
1045 /**
1046  * Set last_avail/used_idx of the vhost virtqueue
1047  *
1048  * @param vid
1049  *  vhost device ID
1050  * @param queue_id
1051  *  vhost queue index
1052  * @param last_avail_idx
1053  *  last_avail_idx to set
1054  * @param last_used_idx
1055  *  last_used_idx to set
1056  * @return
1057  *  0 on success, -1 on failure
1058  */
1059 int
1060 rte_vhost_set_vring_base(int vid, uint16_t queue_id,
1061 		uint16_t last_avail_idx, uint16_t last_used_idx);
1062 
1063 /**
1064  * Register external message handling callbacks
1065  *
1066  * @param vid
1067  *  vhost device ID
1068  * @param ops
1069  *  virtio external callbacks to register
1070  * @param ctx
1071  *  additional context passed to the callbacks
1072  * @return
1073  *  0 on success, -1 on failure
1074  */
1075 int
1076 rte_vhost_extern_callback_register(int vid,
1077 		struct rte_vhost_user_extern_ops const * const ops, void *ctx);
1078 
1079 /**
1080  * Get vdpa device id for vhost device.
1081  *
1082  * @param vid
1083  *  vhost device id
1084  * @return
1085  *  vDPA device pointer on success, NULL on failure
1086  */
1087 struct rte_vdpa_device *
1088 rte_vhost_get_vdpa_device(int vid);
1089 
1090 /**
1091  * Notify the guest that should get virtio configuration space from backend.
1092  *
1093  * @param vid
1094  *  vhost device ID
1095  * @param need_reply
1096  *  wait for the frontend response the status of this operation
1097  * @return
1098  *  0 on success, < 0 on failure
1099  */
1100 int
1101 rte_vhost_backend_config_change(int vid, bool need_reply);
1102 
1103 /**
1104  * Retrieve names of statistics of a Vhost virtqueue.
1105  *
1106  * There is an assumption that 'stat_names' and 'stats' arrays are matched
1107  * by array index: stats_names[i].name => stats[i].value
1108  *
1109  * @param vid
1110  *   vhost device ID
1111  * @param queue_id
1112  *   vhost queue index
1113  * @param name
1114  *   array of at least size elements to be filled.
1115  *   If set to NULL, the function returns the required number of elements.
1116  * @param size
1117  *   The number of elements in stats_names array.
1118  * @return
1119  *  - Success if greater than 0 and lower or equal to *size*. The return value
1120  *    indicates the number of elements filled in the *names* array.
1121  *  - Failure if greater than *size*. The return value indicates the number of
1122  *    elements the *names* array that should be given to succeed.
1123  *  - Failure if lower than 0. The device ID or queue ID is invalid or
1124  +    statistics collection is not enabled.
1125  */
1126 int
1127 rte_vhost_vring_stats_get_names(int vid, uint16_t queue_id,
1128 		struct rte_vhost_stat_name *name, unsigned int size);
1129 
1130 /**
1131  * Retrieve statistics of a Vhost virtqueue.
1132  *
1133  * There is an assumption that 'stat_names' and 'stats' arrays are matched
1134  * by array index: stats_names[i].name => stats[i].value
1135  *
1136  * @param vid
1137  *   vhost device ID
1138  * @param queue_id
1139  *   vhost queue index
1140  * @param stats
1141  *   A pointer to a table of structure of type rte_vhost_stat to be filled with
1142  *   virtqueue statistics ids and values.
1143  * @param n
1144  *   The number of elements in stats array.
1145  * @return
1146  *  - Success if greater than 0 and lower or equal to *n*. The return value
1147  *    indicates the number of elements filled in the *stats* array.
1148  *  - Failure if greater than *n*. The return value indicates the number of
1149  *    elements the *stats* array that should be given to succeed.
1150  *  - Failure if lower than 0. The device ID or queue ID is invalid, or
1151  *    statistics collection is not enabled.
1152  */
1153 int
1154 rte_vhost_vring_stats_get(int vid, uint16_t queue_id,
1155 		struct rte_vhost_stat *stats, unsigned int n);
1156 
1157 /**
1158  * Reset statistics of a Vhost virtqueue.
1159  *
1160  * @param vid
1161  *   vhost device ID
1162  * @param queue_id
1163  *   vhost queue index
1164  * @return
1165  *  - Success if 0. Statistics have been reset.
1166  *  - Failure if lower than 0. The device ID or queue ID is invalid, or
1167  *    statistics collection is not enabled.
1168  */
1169 int
1170 rte_vhost_vring_stats_reset(int vid, uint16_t queue_id);
1171 
1172 #ifdef __cplusplus
1173 }
1174 #endif
1175 
1176 #endif /* _RTE_VHOST_H_ */
1177