1 /* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright(c) 2010-2014 Intel Corporation
5 #ifndef _RTE_INTERRUPTS_H_
6 #define _RTE_INTERRUPTS_H_
10 #include <rte_bitops.h>
11 #include <rte_common.h>
12 #include <rte_compat.h>
13 #include <rte_epoll.h>
18 * The RTE interrupt interface provides functions to register/unregister
19 * callbacks for a specific interrupt.
26 /** Interrupt handle */
27 struct rte_intr_handle;
29 /** Interrupt instance allocation flags
30 * @see rte_intr_instance_alloc
33 /** Interrupt instance will not be shared between primary and secondary processes. */
34 #define RTE_INTR_INSTANCE_F_PRIVATE UINT32_C(0)
35 /** Interrupt instance will be shared between primary and secondary processes. */
36 #define RTE_INTR_INSTANCE_F_SHARED RTE_BIT32(0)
38 #define RTE_MAX_RXTX_INTR_VEC_ID 512
39 #define RTE_INTR_VEC_ZERO_OFFSET 0
40 #define RTE_INTR_VEC_RXTX_OFFSET 1
43 * The interrupt source type, e.g. UIO, VFIO, ALARM etc.
45 enum rte_intr_handle_type {
46 RTE_INTR_HANDLE_UNKNOWN = 0, /**< generic unknown handle */
47 RTE_INTR_HANDLE_UIO, /**< uio device handle */
48 RTE_INTR_HANDLE_UIO_INTX, /**< uio generic handle */
49 RTE_INTR_HANDLE_VFIO_LEGACY, /**< vfio device handle (legacy) */
50 RTE_INTR_HANDLE_VFIO_MSI, /**< vfio device handle (MSI) */
51 RTE_INTR_HANDLE_VFIO_MSIX, /**< vfio device handle (MSIX) */
52 RTE_INTR_HANDLE_ALARM, /**< alarm handle */
53 RTE_INTR_HANDLE_EXT, /**< external handler */
54 RTE_INTR_HANDLE_VDEV, /**< virtual device */
55 RTE_INTR_HANDLE_DEV_EVENT, /**< device event handle */
56 RTE_INTR_HANDLE_VFIO_REQ, /**< VFIO request handle */
57 RTE_INTR_HANDLE_MAX /**< count of elements */
60 /** Function to be registered for the specific interrupt */
61 typedef void (*rte_intr_callback_fn)(void *cb_arg);
64 * Function to call after a callback is unregistered.
65 * Can be used to close fd and free cb_arg.
67 typedef void (*rte_intr_unregister_callback_fn)(struct rte_intr_handle *intr_handle,
71 * It registers the callback for the specific interrupt. Multiple
72 * callbacks can be registered at the same time.
74 * Pointer to the interrupt handle.
78 * address of parameter for callback.
82 * - On failure, a negative value.
84 int rte_intr_callback_register(const struct rte_intr_handle *intr_handle,
85 rte_intr_callback_fn cb, void *cb_arg);
88 * It unregisters the callback according to the specified interrupt handle.
91 * pointer to the interrupt handle.
95 * address of parameter for callback, (void *)-1 means to remove all
96 * registered which has the same callback address.
99 * - On success, return the number of callback entities removed.
100 * - On failure, a negative value.
102 int rte_intr_callback_unregister(const struct rte_intr_handle *intr_handle,
103 rte_intr_callback_fn cb, void *cb_arg);
106 * Unregister the callback according to the specified interrupt handle,
107 * after it's no longer active. Fail if source is not active.
110 * pointer to the interrupt handle.
114 * address of parameter for callback, (void *)-1 means to remove all
115 * registered which has the same callback address.
117 * callback to call before cb is unregistered (optional).
118 * can be used to close fd and free cb_arg.
121 * - On success, return the number of callback entities marked for remove.
122 * - On failure, a negative value.
126 rte_intr_callback_unregister_pending(const struct rte_intr_handle *intr_handle,
127 rte_intr_callback_fn cb_fn, void *cb_arg,
128 rte_intr_unregister_callback_fn ucb_fn);
132 * @b EXPERIMENTAL: this API may change without prior notice
134 * Loop until rte_intr_callback_unregister() succeeds.
135 * After a call to this function,
136 * the callback provided by the specified interrupt handle is unregistered.
139 * pointer to the interrupt handle.
143 * address of parameter for callback, (void *)-1 means to remove all
144 * registered which has the same callback address.
147 * - On success, return the number of callback entities removed.
148 * - On failure, a negative value.
152 rte_intr_callback_unregister_sync(const struct rte_intr_handle *intr_handle,
153 rte_intr_callback_fn cb, void *cb_arg);
156 * It enables the interrupt for the specified handle.
159 * pointer to the interrupt handle.
162 * - On success, zero.
163 * - On failure, a negative value.
165 int rte_intr_enable(const struct rte_intr_handle *intr_handle);
168 * It disables the interrupt for the specified handle.
171 * pointer to the interrupt handle.
174 * - On success, zero.
175 * - On failure, a negative value.
177 int rte_intr_disable(const struct rte_intr_handle *intr_handle);
181 * @b EXPERIMENTAL: this API may change without prior notice
183 * It acknowledges an interrupt raised for the specified handle.
185 * This function should be called at the end of each interrupt handler either
186 * from application or driver, so that currently raised interrupt is acked and
187 * further new interrupts are raised.
190 * pointer to the interrupt handle.
193 * - On success, zero.
194 * - On failure, a negative value.
197 int rte_intr_ack(const struct rte_intr_handle *intr_handle);
201 * @b EXPERIMENTAL: this API may change without prior notice
203 * Check if currently executing in interrupt context
206 * - non zero in case of interrupt context
207 * - zero in case of process context
211 rte_thread_is_intr(void);
215 * @b EXPERIMENTAL: this API may change without prior notice
217 * It allocates memory for interrupt instance. API takes flag as an argument
218 * which define from where memory should be allocated i.e. using DPDK memory
219 * management library APIs or normal heap allocation.
220 * Default memory allocation for event fds and event list array is done which
221 * can be realloced later based on size of MSIX interrupts supported by a PCI
224 * This function should be called from application or driver, before calling
225 * any of the interrupt APIs.
228 * See RTE_INTR_INSTANCE_F_* flags definitions.
231 * - On success, address of interrupt handle.
232 * - On failure, NULL.
235 struct rte_intr_handle *
236 rte_intr_instance_alloc(uint32_t flags);
240 * @b EXPERIMENTAL: this API may change without prior notice
242 * This API is used to free the memory allocated for interrupt handle
246 * Interrupt handle address.
251 rte_intr_instance_free(struct rte_intr_handle *intr_handle);
255 * @b EXPERIMENTAL: this API may change without prior notice
257 * This API is used to set the fd field of interrupt handle with user provided
261 * pointer to the interrupt handle.
263 * file descriptor value provided by user.
266 * - On success, zero.
267 * - On failure, a negative value and rte_errno is set.
271 rte_intr_fd_set(struct rte_intr_handle *intr_handle, int fd);
275 * @b EXPERIMENTAL: this API may change without prior notice
277 * Returns the fd field of the given interrupt handle instance.
280 * pointer to the interrupt handle.
283 * - On success, fd field.
284 * - On failure, a negative value.
288 rte_intr_fd_get(const struct rte_intr_handle *intr_handle);
292 * @b EXPERIMENTAL: this API may change without prior notice
294 * This API is used to set the type field of interrupt handle with user provided
298 * pointer to the interrupt handle.
303 * - On success, zero.
304 * - On failure, a negative value and rte_errno is set.
308 rte_intr_type_set(struct rte_intr_handle *intr_handle,
309 enum rte_intr_handle_type type);
313 * @b EXPERIMENTAL: this API may change without prior notice
315 * Returns the type field of the given interrupt handle instance.
318 * pointer to the interrupt handle.
321 * - On success, interrupt type
322 * - On failure, RTE_INTR_HANDLE_UNKNOWN.
325 enum rte_intr_handle_type
326 rte_intr_type_get(const struct rte_intr_handle *intr_handle);
330 * The function returns the per thread epoll instance.
333 * epfd the epoll instance referred to.
337 rte_intr_tls_epfd(void);
342 * Pointer to the interrupt handle.
344 * Epoll instance fd which the intr vector associated to.
346 * The operation be performed for the vector.
347 * Operation type of {ADD, DEL}.
349 * RX intr vector number added to the epoll instance wait list.
353 * - On success, zero.
354 * - On failure, a negative value.
358 rte_intr_rx_ctl(struct rte_intr_handle *intr_handle,
359 int epfd, int op, unsigned int vec, void *data);
363 * It deletes registered eventfds.
366 * Pointer to the interrupt handle.
370 rte_intr_free_epoll_fd(struct rte_intr_handle *intr_handle);
374 * It enables the packet I/O interrupt event if it's necessary.
375 * It creates event fd for each interrupt vector when MSIX is used,
376 * otherwise it multiplexes a single event fd.
379 * Pointer to the interrupt handle.
381 * Number of interrupt vector trying to enable.
382 * The value 0 is not allowed.
384 * - On success, zero.
385 * - On failure, a negative value.
389 rte_intr_efd_enable(struct rte_intr_handle *intr_handle, uint32_t nb_efd);
393 * It disables the packet I/O interrupt event.
394 * It deletes registered eventfds and closes the open fds.
397 * Pointer to the interrupt handle.
401 rte_intr_efd_disable(struct rte_intr_handle *intr_handle);
405 * The packet I/O interrupt on datapath is enabled or not.
408 * Pointer to the interrupt handle.
412 rte_intr_dp_is_en(struct rte_intr_handle *intr_handle);
416 * The interrupt handle instance allows other causes or not.
417 * Other causes stand for any none packet I/O interrupts.
420 * Pointer to the interrupt handle.
424 rte_intr_allow_others(struct rte_intr_handle *intr_handle);
428 * The multiple interrupt vector capability of interrupt handle instance.
429 * It returns zero if no multiple interrupt vector support.
432 * Pointer to the interrupt handle.
436 rte_intr_cap_multiple(struct rte_intr_handle *intr_handle);
440 * Creates a clone of src by allocating a new handle and copying src content.
443 * Source interrupt handle to be cloned.
446 * - On success, address of interrupt handle.
447 * - On failure, NULL.
450 struct rte_intr_handle *
451 rte_intr_instance_dup(const struct rte_intr_handle *src);
455 * This API is used to set the device fd field of interrupt handle with user
456 * provided dev fd. Device fd corresponds to VFIO device fd or UIO config fd.
459 * pointer to the interrupt handle.
464 * - On success, zero.
465 * - On failure, a negative value and rte_errno is set.
469 rte_intr_dev_fd_set(struct rte_intr_handle *intr_handle, int fd);
473 * Returns the device fd field of the given interrupt handle instance.
476 * pointer to the interrupt handle.
479 * - On success, dev fd.
480 * - On failure, a negative value and rte_errno is set.
484 rte_intr_dev_fd_get(const struct rte_intr_handle *intr_handle);
488 * This API is used to set the max intr field of interrupt handle with user
489 * provided max intr value.
492 * pointer to the interrupt handle.
497 * - On success, zero.
498 * - On failure, a negative value and rte_errno is set.
502 rte_intr_max_intr_set(struct rte_intr_handle *intr_handle, int max_intr);
506 * Returns the max intr field of the given interrupt handle instance.
509 * pointer to the interrupt handle.
512 * - On success, max intr.
513 * - On failure, a negative value and rte_errno is set.
517 rte_intr_max_intr_get(const struct rte_intr_handle *intr_handle);
521 * This API is used to set the number of event fd field of interrupt handle
522 * with user provided available event file descriptor value.
525 * pointer to the interrupt handle.
530 * - On success, zero.
531 * - On failure, a negative value and rte_errno is set.
535 rte_intr_nb_efd_set(struct rte_intr_handle *intr_handle, int nb_efd);
539 * Returns the number of available event fd field of the given interrupt handle
543 * pointer to the interrupt handle.
546 * - On success, nb_efd
547 * - On failure, a negative value and rte_errno is set.
551 rte_intr_nb_efd_get(const struct rte_intr_handle *intr_handle);
555 * Returns the number of interrupt vector field of the given interrupt handle
556 * instance. This field is to configured on device probe time, and based on
557 * this value efds and elist arrays are dynamically allocated. By default
558 * this value is set to RTE_MAX_RXTX_INTR_VEC_ID.
559 * For eg. in case of PCI device, its msix size is queried and efds/elist
560 * arrays are allocated accordingly.
563 * pointer to the interrupt handle.
566 * - On success, nb_intr
567 * - On failure, a negative value and rte_errno is set.
571 rte_intr_nb_intr_get(const struct rte_intr_handle *intr_handle);
575 * This API is used to set the event fd counter size field of interrupt handle
576 * with user provided efd counter size.
579 * pointer to the interrupt handle.
580 * @param efd_counter_size
581 * size of efd counter.
584 * - On success, zero.
585 * - On failure, a negative value and rte_errno is set.
589 rte_intr_efd_counter_size_set(struct rte_intr_handle *intr_handle,
590 uint8_t efd_counter_size);
594 * Returns the event fd counter size field of the given interrupt handle
598 * pointer to the interrupt handle.
601 * - On success, efd_counter_size
602 * - On failure, a negative value and rte_errno is set.
606 rte_intr_efd_counter_size_get(const struct rte_intr_handle *intr_handle);
610 * This API is used to set the event fd array index with the given fd.
613 * pointer to the interrupt handle.
615 * efds array index to be set
620 * - On success, zero.
621 * - On failure, a negative value and rte_errno is set.
625 rte_intr_efds_index_set(struct rte_intr_handle *intr_handle, int index, int fd);
629 * Returns the fd value of event fds array at a given index.
632 * pointer to the interrupt handle.
634 * efds array index to be returned
638 * - On failure, a negative value and rte_errno is set.
642 rte_intr_efds_index_get(const struct rte_intr_handle *intr_handle, int index);
646 * This API is used to set the epoll event object array index with the given
650 * pointer to the interrupt handle.
652 * elist array index to be set
654 * epoll event instance of struct rte_epoll_event
657 * - On success, zero.
658 * - On failure, a negative value and rte_errno is set.
662 rte_intr_elist_index_set(struct rte_intr_handle *intr_handle, int index,
663 struct rte_epoll_event elist);
667 * Returns the address of epoll event instance from elist array at a given
671 * pointer to the interrupt handle.
673 * elist array index to be returned
676 * - On success, elist
677 * - On failure, a negative value and rte_errno is set.
680 struct rte_epoll_event *
681 rte_intr_elist_index_get(struct rte_intr_handle *intr_handle, int index);
685 * Allocates the memory of interrupt vector list array, with size defining the
686 * number of elements required in the array.
689 * pointer to the interrupt handle.
691 * Name assigned to the allocation, or NULL.
693 * Number of element required in the array.
697 * - On failure, a negative value and rte_errno is set.
701 rte_intr_vec_list_alloc(struct rte_intr_handle *intr_handle, const char *name,
706 * Sets the vector value at given index of interrupt vector list field of given
710 * pointer to the interrupt handle.
712 * intr_vec array index to be set
714 * Interrupt vector value.
718 * - On failure, a negative value and rte_errno is set.
722 rte_intr_vec_list_index_set(struct rte_intr_handle *intr_handle, int index,
727 * Returns the vector value at the given index of interrupt vector list array.
730 * pointer to the interrupt handle.
732 * intr_vec array index to be returned
735 * - On success, interrupt vector
736 * - On failure, a negative value and rte_errno is set.
740 rte_intr_vec_list_index_get(const struct rte_intr_handle *intr_handle,
745 * Frees the memory allocated for interrupt vector list array.
748 * pointer to the interrupt handle.
752 * - On failure, a negative value and rte_errno is set.
756 rte_intr_vec_list_free(struct rte_intr_handle *intr_handle);
760 * Reallocates the size efds and elist array based on size provided by user.
761 * By default efds and elist array are allocated with default size
762 * RTE_MAX_RXTX_INTR_VEC_ID on interrupt handle array creation. Later on device
763 * probe, device may have capability of more interrupts than
764 * RTE_MAX_RXTX_INTR_VEC_ID. Using this API, PMDs can reallocate the arrays as
765 * per the max interrupts capability of device.
768 * pointer to the interrupt handle.
770 * efds and elist array size.
774 * - On failure, a negative value and rte_errno is set.
778 rte_intr_event_list_update(struct rte_intr_handle *intr_handle, int size);
782 * This API returns the Windows handle of the given interrupt instance.
785 * pointer to the interrupt handle.
788 * - On success, Windows handle.
789 * - On failure, NULL.
793 rte_intr_instance_windows_handle_get(struct rte_intr_handle *intr_handle);
797 * This API set the Windows handle for the given interrupt instance.
800 * pointer to the interrupt handle.
801 * @param windows_handle
802 * Windows handle to be set.
806 * - On failure, a negative value and rte_errno is set.
810 rte_intr_instance_windows_handle_set(struct rte_intr_handle *intr_handle,
811 void *windows_handle);