Branch data Line data Source code
1 : : /* SPDX-License-Identifier: BSD-3-Clause
2 : : * Copyright(C) 2021 Marvell.
3 : : */
4 : :
5 : : #include <stdlib.h>
6 : : #include <string.h>
7 : :
8 : : #include <rte_errno.h>
9 : : #include <rte_interrupts.h>
10 : : #include <rte_log.h>
11 : : #include <rte_malloc.h>
12 : :
13 : : #include <eal_export.h>
14 : : #include "eal_interrupts.h"
15 : : #include "eal_private.h"
16 : :
17 : : /* Macros to check for valid interrupt handle */
18 : : #define CHECK_VALID_INTR_HANDLE(intr_handle) do { \
19 : : if (intr_handle == NULL) { \
20 : : EAL_LOG(DEBUG, "Interrupt instance unallocated"); \
21 : : rte_errno = EINVAL; \
22 : : goto fail; \
23 : : } \
24 : : } while (0)
25 : :
26 : : #define RTE_INTR_INSTANCE_KNOWN_FLAGS (RTE_INTR_INSTANCE_F_PRIVATE \
27 : : | RTE_INTR_INSTANCE_F_SHARED \
28 : : )
29 : :
30 : : #define RTE_INTR_INSTANCE_USES_RTE_MEMORY(flags) \
31 : : (!!(flags & RTE_INTR_INSTANCE_F_SHARED))
32 : :
33 : : RTE_EXPORT_SYMBOL(rte_intr_instance_alloc)
34 : 548 : struct rte_intr_handle *rte_intr_instance_alloc(uint32_t flags)
35 : : {
36 : : struct rte_intr_handle *intr_handle;
37 : : bool uses_rte_memory;
38 : :
39 : : /* Check the flag passed by user, it should be part of the
40 : : * defined flags.
41 : : */
42 [ - + ]: 548 : if ((flags & ~RTE_INTR_INSTANCE_KNOWN_FLAGS) != 0) {
43 : 0 : EAL_LOG(DEBUG, "Invalid alloc flag passed 0x%x", flags);
44 : 0 : rte_errno = EINVAL;
45 : 0 : return NULL;
46 : : }
47 : :
48 : 548 : uses_rte_memory = RTE_INTR_INSTANCE_USES_RTE_MEMORY(flags);
49 [ - + ]: 548 : if (uses_rte_memory)
50 : 0 : intr_handle = rte_zmalloc(NULL, sizeof(*intr_handle), 0);
51 : : else
52 : 548 : intr_handle = calloc(1, sizeof(*intr_handle));
53 [ - + ]: 548 : if (intr_handle == NULL) {
54 : 0 : EAL_LOG(ERR, "Failed to allocate intr_handle");
55 : 0 : rte_errno = ENOMEM;
56 : 0 : return NULL;
57 : : }
58 : :
59 [ - + ]: 548 : if (uses_rte_memory) {
60 : 0 : intr_handle->efds = rte_zmalloc(NULL,
61 : : RTE_MAX_RXTX_INTR_VEC_ID * sizeof(int), 0);
62 : : } else {
63 : 548 : intr_handle->efds = calloc(RTE_MAX_RXTX_INTR_VEC_ID,
64 : : sizeof(int));
65 : : }
66 [ - + ]: 548 : if (intr_handle->efds == NULL) {
67 : 0 : EAL_LOG(ERR, "Fail to allocate event fd list");
68 : 0 : rte_errno = ENOMEM;
69 : 0 : goto fail;
70 : : }
71 : :
72 [ - + ]: 548 : if (uses_rte_memory) {
73 : 0 : intr_handle->elist = rte_zmalloc(NULL,
74 : : RTE_MAX_RXTX_INTR_VEC_ID * sizeof(struct rte_epoll_event),
75 : : 0);
76 : : } else {
77 : 548 : intr_handle->elist = calloc(RTE_MAX_RXTX_INTR_VEC_ID,
78 : : sizeof(struct rte_epoll_event));
79 : : }
80 [ - + ]: 548 : if (intr_handle->elist == NULL) {
81 : 0 : EAL_LOG(ERR, "fail to allocate event fd list");
82 : 0 : rte_errno = ENOMEM;
83 : 0 : goto fail;
84 : : }
85 : :
86 : 548 : intr_handle->alloc_flags = flags;
87 : 548 : intr_handle->nb_intr = RTE_MAX_RXTX_INTR_VEC_ID;
88 : :
89 : 548 : return intr_handle;
90 : 0 : fail:
91 [ # # ]: 0 : if (uses_rte_memory) {
92 : 0 : rte_free(intr_handle->efds);
93 : 0 : rte_free(intr_handle);
94 : : } else {
95 : 0 : free(intr_handle->efds);
96 : 0 : free(intr_handle);
97 : : }
98 : : return NULL;
99 : : }
100 : :
101 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_instance_dup)
102 : 7 : struct rte_intr_handle *rte_intr_instance_dup(const struct rte_intr_handle *src)
103 : : {
104 : : struct rte_intr_handle *intr_handle;
105 : :
106 [ - + ]: 7 : if (src == NULL) {
107 : 0 : EAL_LOG(DEBUG, "Source interrupt instance unallocated");
108 : 0 : rte_errno = EINVAL;
109 : 0 : return NULL;
110 : : }
111 : :
112 : 7 : intr_handle = rte_intr_instance_alloc(src->alloc_flags);
113 [ + - ]: 7 : if (intr_handle != NULL) {
114 : 7 : intr_handle->fd = src->fd;
115 : 7 : intr_handle->dev_fd = src->dev_fd;
116 : 7 : intr_handle->type = src->type;
117 : 7 : intr_handle->max_intr = src->max_intr;
118 : 7 : intr_handle->nb_efd = src->nb_efd;
119 : 7 : intr_handle->efd_counter_size = src->efd_counter_size;
120 : 7 : memcpy(intr_handle->efds, src->efds, src->nb_intr);
121 : 7 : memcpy(intr_handle->elist, src->elist, src->nb_intr);
122 : : }
123 : :
124 : : return intr_handle;
125 : : }
126 : :
127 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_event_list_update)
128 : 0 : int rte_intr_event_list_update(struct rte_intr_handle *intr_handle, int size)
129 : : {
130 : : struct rte_epoll_event *tmp_elist;
131 : : bool uses_rte_memory;
132 : : int *tmp_efds;
133 : :
134 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
135 : :
136 [ # # ]: 0 : if (size == 0) {
137 : 0 : EAL_LOG(DEBUG, "Size can't be zero");
138 : 0 : rte_errno = EINVAL;
139 : 0 : goto fail;
140 : : }
141 : :
142 : : uses_rte_memory =
143 : 0 : RTE_INTR_INSTANCE_USES_RTE_MEMORY(intr_handle->alloc_flags);
144 [ # # ]: 0 : if (uses_rte_memory) {
145 : 0 : tmp_efds = rte_realloc(intr_handle->efds, size * sizeof(int),
146 : : 0);
147 : : } else {
148 : 0 : tmp_efds = realloc(intr_handle->efds, size * sizeof(int));
149 : : }
150 [ # # ]: 0 : if (tmp_efds == NULL) {
151 : 0 : EAL_LOG(ERR, "Failed to realloc the efds list");
152 : 0 : rte_errno = ENOMEM;
153 : 0 : goto fail;
154 : : }
155 : 0 : intr_handle->efds = tmp_efds;
156 : :
157 [ # # ]: 0 : if (uses_rte_memory) {
158 : 0 : tmp_elist = rte_realloc(intr_handle->elist,
159 : : size * sizeof(struct rte_epoll_event), 0);
160 : : } else {
161 : 0 : tmp_elist = realloc(intr_handle->elist,
162 : : size * sizeof(struct rte_epoll_event));
163 : : }
164 [ # # ]: 0 : if (tmp_elist == NULL) {
165 : 0 : EAL_LOG(ERR, "Failed to realloc the event list");
166 : 0 : rte_errno = ENOMEM;
167 : 0 : goto fail;
168 : : }
169 : 0 : intr_handle->elist = tmp_elist;
170 : :
171 : 0 : intr_handle->nb_intr = size;
172 : :
173 : 0 : return 0;
174 : 0 : fail:
175 : 0 : return -rte_errno;
176 : : }
177 : :
178 : : RTE_EXPORT_SYMBOL(rte_intr_instance_free)
179 : 14655 : void rte_intr_instance_free(struct rte_intr_handle *intr_handle)
180 : : {
181 [ + + ]: 14655 : if (intr_handle == NULL)
182 : : return;
183 [ - + ]: 546 : if (RTE_INTR_INSTANCE_USES_RTE_MEMORY(intr_handle->alloc_flags)) {
184 : 0 : rte_free(intr_handle->efds);
185 : 0 : rte_free(intr_handle->elist);
186 : 0 : rte_free(intr_handle);
187 : : } else {
188 : 546 : free(intr_handle->efds);
189 : 546 : free(intr_handle->elist);
190 : 546 : free(intr_handle);
191 : : }
192 : : }
193 : :
194 : : RTE_EXPORT_SYMBOL(rte_intr_fd_set)
195 : 191 : int rte_intr_fd_set(struct rte_intr_handle *intr_handle, int fd)
196 : : {
197 [ - + ]: 191 : CHECK_VALID_INTR_HANDLE(intr_handle);
198 : :
199 : 191 : intr_handle->fd = fd;
200 : :
201 : 191 : return 0;
202 : : fail:
203 : 0 : return -rte_errno;
204 : : }
205 : :
206 : : RTE_EXPORT_SYMBOL(rte_intr_fd_get)
207 : 1624646 : int rte_intr_fd_get(const struct rte_intr_handle *intr_handle)
208 : : {
209 [ + + ]: 1624646 : CHECK_VALID_INTR_HANDLE(intr_handle);
210 : :
211 : 1624644 : return intr_handle->fd;
212 : : fail:
213 : 2 : return -1;
214 : : }
215 : :
216 : : RTE_EXPORT_SYMBOL(rte_intr_type_set)
217 : 191 : int rte_intr_type_set(struct rte_intr_handle *intr_handle,
218 : : enum rte_intr_handle_type type)
219 : : {
220 [ - + ]: 191 : CHECK_VALID_INTR_HANDLE(intr_handle);
221 : :
222 : 191 : intr_handle->type = type;
223 : :
224 : 191 : return 0;
225 : : fail:
226 : 0 : return -rte_errno;
227 : : }
228 : :
229 : : RTE_EXPORT_SYMBOL(rte_intr_type_get)
230 : 696182 : enum rte_intr_handle_type rte_intr_type_get(
231 : : const struct rte_intr_handle *intr_handle)
232 : : {
233 [ - + ]: 696182 : CHECK_VALID_INTR_HANDLE(intr_handle);
234 : :
235 : 696182 : return intr_handle->type;
236 : : fail:
237 : 0 : return RTE_INTR_HANDLE_UNKNOWN;
238 : : }
239 : :
240 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_dev_fd_set)
241 : 0 : int rte_intr_dev_fd_set(struct rte_intr_handle *intr_handle, int fd)
242 : : {
243 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
244 : :
245 : 0 : intr_handle->dev_fd = fd;
246 : :
247 : 0 : return 0;
248 : : fail:
249 : 0 : return -rte_errno;
250 : : }
251 : :
252 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_dev_fd_get)
253 : 12 : int rte_intr_dev_fd_get(const struct rte_intr_handle *intr_handle)
254 : : {
255 [ - + ]: 12 : CHECK_VALID_INTR_HANDLE(intr_handle);
256 : :
257 : 12 : return intr_handle->dev_fd;
258 : : fail:
259 : 0 : return -1;
260 : : }
261 : :
262 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_max_intr_set)
263 : 0 : int rte_intr_max_intr_set(struct rte_intr_handle *intr_handle,
264 : : int max_intr)
265 : : {
266 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
267 : :
268 [ # # ]: 0 : if (max_intr > intr_handle->nb_intr) {
269 : 0 : EAL_LOG(DEBUG, "Maximum interrupt vector ID (%d) exceeds "
270 : : "the number of available events (%d)", max_intr,
271 : : intr_handle->nb_intr);
272 : 0 : rte_errno = ERANGE;
273 : 0 : goto fail;
274 : : }
275 : :
276 : 0 : intr_handle->max_intr = max_intr;
277 : :
278 : 0 : return 0;
279 : 0 : fail:
280 : 0 : return -rte_errno;
281 : : }
282 : :
283 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_max_intr_get)
284 : 0 : int rte_intr_max_intr_get(const struct rte_intr_handle *intr_handle)
285 : : {
286 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
287 : :
288 : 0 : return intr_handle->max_intr;
289 : : fail:
290 : 0 : return -rte_errno;
291 : : }
292 : :
293 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_nb_efd_set)
294 : 0 : int rte_intr_nb_efd_set(struct rte_intr_handle *intr_handle, int nb_efd)
295 : : {
296 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
297 : :
298 : 0 : intr_handle->nb_efd = nb_efd;
299 : :
300 : 0 : return 0;
301 : : fail:
302 : 0 : return -rte_errno;
303 : : }
304 : :
305 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_nb_efd_get)
306 : 0 : int rte_intr_nb_efd_get(const struct rte_intr_handle *intr_handle)
307 : : {
308 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
309 : :
310 : 0 : return intr_handle->nb_efd;
311 : : fail:
312 : 0 : return -rte_errno;
313 : : }
314 : :
315 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_nb_intr_get)
316 : 0 : int rte_intr_nb_intr_get(const struct rte_intr_handle *intr_handle)
317 : : {
318 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
319 : :
320 : 0 : return intr_handle->nb_intr;
321 : : fail:
322 : 0 : return -rte_errno;
323 : : }
324 : :
325 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_efd_counter_size_set)
326 : 0 : int rte_intr_efd_counter_size_set(struct rte_intr_handle *intr_handle,
327 : : uint8_t efd_counter_size)
328 : : {
329 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
330 : :
331 : 0 : intr_handle->efd_counter_size = efd_counter_size;
332 : :
333 : 0 : return 0;
334 : : fail:
335 : 0 : return -rte_errno;
336 : : }
337 : :
338 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_efd_counter_size_get)
339 : 0 : int rte_intr_efd_counter_size_get(const struct rte_intr_handle *intr_handle)
340 : : {
341 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
342 : :
343 : 0 : return intr_handle->efd_counter_size;
344 : : fail:
345 : 0 : return -rte_errno;
346 : : }
347 : :
348 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_efds_index_get)
349 : 0 : int rte_intr_efds_index_get(const struct rte_intr_handle *intr_handle,
350 : : int index)
351 : : {
352 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
353 : :
354 [ # # ]: 0 : if (index >= intr_handle->nb_intr) {
355 : 0 : EAL_LOG(DEBUG, "Invalid index %d, max limit %d", index,
356 : : intr_handle->nb_intr);
357 : 0 : rte_errno = EINVAL;
358 : 0 : goto fail;
359 : : }
360 : :
361 : 0 : return intr_handle->efds[index];
362 : 0 : fail:
363 : 0 : return -rte_errno;
364 : : }
365 : :
366 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_efds_index_set)
367 : 0 : int rte_intr_efds_index_set(struct rte_intr_handle *intr_handle,
368 : : int index, int fd)
369 : : {
370 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
371 : :
372 [ # # ]: 0 : if (index >= intr_handle->nb_intr) {
373 : 0 : EAL_LOG(DEBUG, "Invalid index %d, max limit %d", index,
374 : : intr_handle->nb_intr);
375 : 0 : rte_errno = ERANGE;
376 : 0 : goto fail;
377 : : }
378 : :
379 : 0 : intr_handle->efds[index] = fd;
380 : :
381 : 0 : return 0;
382 : 0 : fail:
383 : 0 : return -rte_errno;
384 : : }
385 : :
386 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_elist_index_get)
387 : 0 : struct rte_epoll_event *rte_intr_elist_index_get(
388 : : struct rte_intr_handle *intr_handle, int index)
389 : : {
390 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
391 : :
392 [ # # ]: 0 : if (index >= intr_handle->nb_intr) {
393 : 0 : EAL_LOG(DEBUG, "Invalid index %d, max limit %d", index,
394 : : intr_handle->nb_intr);
395 : 0 : rte_errno = ERANGE;
396 : 0 : goto fail;
397 : : }
398 : :
399 : 0 : return &intr_handle->elist[index];
400 : : fail:
401 : : return NULL;
402 : : }
403 : :
404 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_elist_index_set)
405 : 0 : int rte_intr_elist_index_set(struct rte_intr_handle *intr_handle,
406 : : int index, struct rte_epoll_event elist)
407 : : {
408 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
409 : :
410 [ # # ]: 0 : if (index >= intr_handle->nb_intr) {
411 : 0 : EAL_LOG(DEBUG, "Invalid index %d, max limit %d", index,
412 : : intr_handle->nb_intr);
413 : 0 : rte_errno = ERANGE;
414 : 0 : goto fail;
415 : : }
416 : :
417 : 0 : intr_handle->elist[index] = elist;
418 : :
419 : 0 : return 0;
420 : 0 : fail:
421 : 0 : return -rte_errno;
422 : : }
423 : :
424 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_vec_list_alloc)
425 : 0 : int rte_intr_vec_list_alloc(struct rte_intr_handle *intr_handle,
426 : : const char *name, int size)
427 : : {
428 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
429 : :
430 : : /* Vector list already allocated */
431 [ # # ]: 0 : if (intr_handle->intr_vec != NULL)
432 : : return 0;
433 : :
434 [ # # ]: 0 : if (size > intr_handle->nb_intr) {
435 : 0 : EAL_LOG(DEBUG, "Invalid size %d, max limit %d", size,
436 : : intr_handle->nb_intr);
437 : 0 : rte_errno = ERANGE;
438 : 0 : goto fail;
439 : : }
440 : :
441 [ # # ]: 0 : if (RTE_INTR_INSTANCE_USES_RTE_MEMORY(intr_handle->alloc_flags))
442 : 0 : intr_handle->intr_vec = rte_zmalloc(name, size * sizeof(int), 0);
443 : : else
444 : 0 : intr_handle->intr_vec = calloc(size, sizeof(int));
445 [ # # ]: 0 : if (intr_handle->intr_vec == NULL) {
446 : 0 : EAL_LOG(ERR, "Failed to allocate %d intr_vec", size);
447 : 0 : rte_errno = ENOMEM;
448 : 0 : goto fail;
449 : : }
450 : :
451 : 0 : intr_handle->vec_list_size = size;
452 : :
453 : 0 : return 0;
454 : 0 : fail:
455 : 0 : return -rte_errno;
456 : : }
457 : :
458 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_vec_list_index_get)
459 : 0 : int rte_intr_vec_list_index_get(const struct rte_intr_handle *intr_handle,
460 : : int index)
461 : : {
462 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
463 : :
464 [ # # ]: 0 : if (index >= intr_handle->vec_list_size) {
465 : 0 : EAL_LOG(DEBUG, "Index %d greater than vec list size %d",
466 : : index, intr_handle->vec_list_size);
467 : 0 : rte_errno = ERANGE;
468 : 0 : goto fail;
469 : : }
470 : :
471 : 0 : return intr_handle->intr_vec[index];
472 : 0 : fail:
473 : 0 : return -rte_errno;
474 : : }
475 : :
476 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_vec_list_index_set)
477 : 0 : int rte_intr_vec_list_index_set(struct rte_intr_handle *intr_handle,
478 : : int index, int vec)
479 : : {
480 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
481 : :
482 [ # # ]: 0 : if (index >= intr_handle->vec_list_size) {
483 : 0 : EAL_LOG(DEBUG, "Index %d greater than vec list size %d",
484 : : index, intr_handle->vec_list_size);
485 : 0 : rte_errno = ERANGE;
486 : 0 : goto fail;
487 : : }
488 : :
489 : 0 : intr_handle->intr_vec[index] = vec;
490 : :
491 : 0 : return 0;
492 : 0 : fail:
493 : 0 : return -rte_errno;
494 : : }
495 : :
496 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_vec_list_free)
497 : 0 : void rte_intr_vec_list_free(struct rte_intr_handle *intr_handle)
498 : : {
499 [ # # ]: 0 : if (intr_handle == NULL)
500 : : return;
501 [ # # ]: 0 : if (RTE_INTR_INSTANCE_USES_RTE_MEMORY(intr_handle->alloc_flags))
502 : 0 : rte_free(intr_handle->intr_vec);
503 : : else
504 : 0 : free(intr_handle->intr_vec);
505 : 0 : intr_handle->intr_vec = NULL;
506 : 0 : intr_handle->vec_list_size = 0;
507 : : }
508 : :
509 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_instance_windows_handle_get)
510 : 0 : void *rte_intr_instance_windows_handle_get(struct rte_intr_handle *intr_handle)
511 : : {
512 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
513 : :
514 : 0 : return intr_handle->windows_handle;
515 : : fail:
516 : 0 : return NULL;
517 : : }
518 : :
519 : : RTE_EXPORT_INTERNAL_SYMBOL(rte_intr_instance_windows_handle_set)
520 : 0 : int rte_intr_instance_windows_handle_set(struct rte_intr_handle *intr_handle,
521 : : void *windows_handle)
522 : : {
523 [ # # ]: 0 : CHECK_VALID_INTR_HANDLE(intr_handle);
524 : :
525 : 0 : intr_handle->windows_handle = windows_handle;
526 : :
527 : 0 : return 0;
528 : : fail:
529 : 0 : return -rte_errno;
530 : : }
|