]>
Commit | Line | Data |
---|---|---|
11fdf7f2 TL |
1 | /* SPDX-License-Identifier: BSD-3-Clause |
2 | * Copyright(c) 2014 6WIND S.A. | |
3 | */ | |
4 | ||
5 | #ifndef _RTE_DEV_H_ | |
6 | #define _RTE_DEV_H_ | |
7 | ||
8 | /** | |
9 | * @file | |
10 | * | |
11 | * RTE PMD Driver Registration Interface | |
12 | * | |
13 | * This file manages the list of device drivers. | |
14 | */ | |
15 | ||
16 | #ifdef __cplusplus | |
17 | extern "C" { | |
18 | #endif | |
19 | ||
20 | #include <stdio.h> | |
21 | #include <sys/queue.h> | |
22 | ||
23 | #include <rte_config.h> | |
24 | #include <rte_compat.h> | |
25 | #include <rte_log.h> | |
26 | ||
27 | /** | |
28 | * The device event type. | |
29 | */ | |
30 | enum rte_dev_event_type { | |
31 | RTE_DEV_EVENT_ADD, /**< device being added */ | |
32 | RTE_DEV_EVENT_REMOVE, /**< device being removed */ | |
33 | RTE_DEV_EVENT_MAX /**< max value of this enum */ | |
34 | }; | |
35 | ||
36 | struct rte_dev_event { | |
37 | enum rte_dev_event_type type; /**< device event type */ | |
38 | int subsystem; /**< subsystem id */ | |
39 | char *devname; /**< device name */ | |
40 | }; | |
41 | ||
9f95a23c | 42 | typedef void (*rte_dev_event_cb_fn)(const char *device_name, |
11fdf7f2 TL |
43 | enum rte_dev_event_type event, |
44 | void *cb_arg); | |
45 | ||
11fdf7f2 TL |
46 | /* Macros to check for invalid function pointers */ |
47 | #define RTE_FUNC_PTR_OR_ERR_RET(func, retval) do { \ | |
9f95a23c | 48 | if ((func) == NULL) \ |
11fdf7f2 | 49 | return retval; \ |
11fdf7f2 TL |
50 | } while (0) |
51 | ||
52 | #define RTE_FUNC_PTR_OR_RET(func) do { \ | |
9f95a23c | 53 | if ((func) == NULL) \ |
11fdf7f2 | 54 | return; \ |
11fdf7f2 TL |
55 | } while (0) |
56 | ||
57 | /** | |
58 | * Device driver. | |
59 | */ | |
60 | enum rte_kernel_driver { | |
61 | RTE_KDRV_UNKNOWN = 0, | |
62 | RTE_KDRV_IGB_UIO, | |
63 | RTE_KDRV_VFIO, | |
64 | RTE_KDRV_UIO_GENERIC, | |
65 | RTE_KDRV_NIC_UIO, | |
66 | RTE_KDRV_NONE, | |
67 | }; | |
68 | ||
69 | /** | |
70 | * Device policies. | |
71 | */ | |
72 | enum rte_dev_policy { | |
73 | RTE_DEV_WHITELISTED, | |
74 | RTE_DEV_BLACKLISTED, | |
75 | }; | |
76 | ||
77 | /** | |
78 | * A generic memory resource representation. | |
79 | */ | |
80 | struct rte_mem_resource { | |
81 | uint64_t phys_addr; /**< Physical address, 0 if not resource. */ | |
82 | uint64_t len; /**< Length of the resource. */ | |
83 | void *addr; /**< Virtual address, NULL when not mapped. */ | |
84 | }; | |
85 | ||
86 | /** | |
87 | * A structure describing a device driver. | |
88 | */ | |
89 | struct rte_driver { | |
90 | TAILQ_ENTRY(rte_driver) next; /**< Next in list. */ | |
91 | const char *name; /**< Driver name. */ | |
92 | const char *alias; /**< Driver alias. */ | |
93 | }; | |
94 | ||
95 | /* | |
96 | * Internal identifier length | |
97 | * Sufficiently large to allow for UUID or PCI address | |
98 | */ | |
99 | #define RTE_DEV_NAME_MAX_LEN 64 | |
100 | ||
101 | /** | |
102 | * A structure describing a generic device. | |
103 | */ | |
104 | struct rte_device { | |
105 | TAILQ_ENTRY(rte_device) next; /**< Next device */ | |
106 | const char *name; /**< Device name */ | |
9f95a23c TL |
107 | const struct rte_driver *driver; /**< Driver assigned after probing */ |
108 | const struct rte_bus *bus; /**< Bus handle assigned on scan */ | |
11fdf7f2 | 109 | int numa_node; /**< NUMA node connection */ |
9f95a23c | 110 | struct rte_devargs *devargs; /**< Arguments for latest probing */ |
11fdf7f2 TL |
111 | }; |
112 | ||
113 | /** | |
9f95a23c | 114 | * Query status of a device. |
11fdf7f2 TL |
115 | * |
116 | * @param dev | |
9f95a23c | 117 | * Generic device pointer. |
11fdf7f2 | 118 | * @return |
9f95a23c | 119 | * (int)true if already probed successfully, 0 otherwise. |
11fdf7f2 | 120 | */ |
9f95a23c | 121 | int rte_dev_is_probed(const struct rte_device *dev); |
11fdf7f2 TL |
122 | |
123 | /** | |
11fdf7f2 TL |
124 | * Hotplug add a given device to a specific bus. |
125 | * | |
9f95a23c TL |
126 | * In multi-process, it will request other processes to add the same device. |
127 | * A failure, in any process, will rollback the action | |
128 | * | |
11fdf7f2 TL |
129 | * @param busname |
130 | * The bus name the device is added to. | |
131 | * @param devname | |
132 | * The device name. Based on this device name, eal will identify a driver | |
133 | * capable of handling it and pass it to the driver probing function. | |
9f95a23c | 134 | * @param drvargs |
11fdf7f2 TL |
135 | * Device arguments to be passed to the driver. |
136 | * @return | |
137 | * 0 on success, negative on error. | |
138 | */ | |
9f95a23c TL |
139 | int rte_eal_hotplug_add(const char *busname, const char *devname, |
140 | const char *drvargs); | |
11fdf7f2 TL |
141 | |
142 | /** | |
9f95a23c TL |
143 | * Add matching devices. |
144 | * | |
145 | * In multi-process, it will request other processes to add the same device. | |
146 | * A failure, in any process, will rollback the action | |
11fdf7f2 | 147 | * |
9f95a23c TL |
148 | * @param devargs |
149 | * Device arguments including bus, class and driver properties. | |
150 | * @return | |
151 | * 0 on success, negative on error. | |
152 | */ | |
153 | int rte_dev_probe(const char *devargs); | |
154 | ||
155 | /** | |
11fdf7f2 TL |
156 | * Hotplug remove a given device from a specific bus. |
157 | * | |
9f95a23c TL |
158 | * In multi-process, it will request other processes to remove the same device. |
159 | * A failure, in any process, will rollback the action | |
160 | * | |
11fdf7f2 TL |
161 | * @param busname |
162 | * The bus name the device is removed from. | |
163 | * @param devname | |
164 | * The device name being removed. | |
165 | * @return | |
166 | * 0 on success, negative on error. | |
167 | */ | |
9f95a23c TL |
168 | int rte_eal_hotplug_remove(const char *busname, const char *devname); |
169 | ||
170 | /** | |
171 | * Remove one device. | |
172 | * | |
173 | * In multi-process, it will request other processes to remove the same device. | |
174 | * A failure, in any process, will rollback the action | |
175 | * | |
176 | * @param dev | |
177 | * Data structure of the device to remove. | |
178 | * @return | |
179 | * 0 on success, negative on error. | |
180 | */ | |
181 | int rte_dev_remove(struct rte_device *dev); | |
11fdf7f2 TL |
182 | |
183 | /** | |
184 | * Device comparison function. | |
185 | * | |
186 | * This type of function is used to compare an rte_device with arbitrary | |
187 | * data. | |
188 | * | |
189 | * @param dev | |
190 | * Device handle. | |
191 | * | |
192 | * @param data | |
193 | * Data to compare against. The type of this parameter is determined by | |
194 | * the kind of comparison performed by the function. | |
195 | * | |
196 | * @return | |
197 | * 0 if the device matches the data. | |
198 | * !0 if the device does not match. | |
199 | * <0 if ordering is possible and the device is lower than the data. | |
200 | * >0 if ordering is possible and the device is greater than the data. | |
201 | */ | |
202 | typedef int (*rte_dev_cmp_t)(const struct rte_device *dev, const void *data); | |
203 | ||
204 | #define RTE_PMD_EXPORT_NAME_ARRAY(n, idx) n##idx[] | |
205 | ||
206 | #define RTE_PMD_EXPORT_NAME(name, idx) \ | |
207 | static const char RTE_PMD_EXPORT_NAME_ARRAY(this_pmd_name, idx) \ | |
208 | __attribute__((used)) = RTE_STR(name) | |
209 | ||
210 | #define DRV_EXP_TAG(name, tag) __##name##_##tag | |
211 | ||
212 | #define RTE_PMD_REGISTER_PCI_TABLE(name, table) \ | |
213 | static const char DRV_EXP_TAG(name, pci_tbl_export)[] __attribute__((used)) = \ | |
214 | RTE_STR(table) | |
215 | ||
216 | #define RTE_PMD_REGISTER_PARAM_STRING(name, str) \ | |
217 | static const char DRV_EXP_TAG(name, param_string_export)[] \ | |
218 | __attribute__((used)) = str | |
219 | ||
220 | /** | |
221 | * Advertise the list of kernel modules required to run this driver | |
222 | * | |
223 | * This string lists the kernel modules required for the devices | |
224 | * associated to a PMD. The format of each line of the string is: | |
225 | * "<device-pattern> <kmod-expression>". | |
226 | * | |
227 | * The possible formats for the device pattern are: | |
228 | * "*" all devices supported by this driver | |
229 | * "pci:*" all PCI devices supported by this driver | |
230 | * "pci:v8086:d*:sv*:sd*" all PCI devices supported by this driver | |
231 | * whose vendor id is 0x8086. | |
232 | * | |
233 | * The format of the kernel modules list is a parenthesed expression | |
234 | * containing logical-and (&) and logical-or (|). | |
235 | * | |
236 | * The device pattern and the kmod expression are separated by a space. | |
237 | * | |
238 | * Example: | |
239 | * - "* igb_uio | uio_pci_generic | vfio" | |
240 | */ | |
241 | #define RTE_PMD_REGISTER_KMOD_DEP(name, str) \ | |
242 | static const char DRV_EXP_TAG(name, kmod_dep_export)[] \ | |
243 | __attribute__((used)) = str | |
244 | ||
245 | /** | |
246 | * Iteration context. | |
247 | * | |
248 | * This context carries over the current iteration state. | |
249 | */ | |
250 | struct rte_dev_iterator { | |
251 | const char *dev_str; /**< device string. */ | |
252 | const char *bus_str; /**< bus-related part of device string. */ | |
253 | const char *cls_str; /**< class-related part of device string. */ | |
254 | struct rte_bus *bus; /**< bus handle. */ | |
255 | struct rte_class *cls; /**< class handle. */ | |
256 | struct rte_device *device; /**< current position. */ | |
257 | void *class_device; /**< additional specialized context. */ | |
258 | }; | |
259 | ||
260 | /** | |
261 | * Device iteration function. | |
262 | * | |
263 | * Find the next device matching properties passed in parameters. | |
264 | * The function takes an additional ``start`` parameter, that is | |
265 | * used as starting context when relevant. | |
266 | * | |
267 | * The function returns the current element in the iteration. | |
268 | * This return value will potentially be used as a start parameter | |
269 | * in subsequent calls to the function. | |
270 | * | |
271 | * The additional iterator parameter is only there if a specific | |
272 | * implementation needs additional context. It must not be modified by | |
273 | * the iteration function itself. | |
274 | * | |
275 | * @param start | |
276 | * Starting iteration context. | |
277 | * | |
278 | * @param devstr | |
279 | * Device description string. | |
280 | * | |
281 | * @param it | |
282 | * Device iterator. | |
283 | * | |
284 | * @return | |
285 | * The address of the current element matching the device description | |
286 | * string. | |
287 | */ | |
288 | typedef void *(*rte_dev_iterate_t)(const void *start, | |
289 | const char *devstr, | |
290 | const struct rte_dev_iterator *it); | |
291 | ||
292 | /** | |
293 | * Initializes a device iterator. | |
294 | * | |
295 | * This iterator allows accessing a list of devices matching a criteria. | |
296 | * The device matching is made among all buses and classes currently registered, | |
297 | * filtered by the device description given as parameter. | |
298 | * | |
299 | * This function will not allocate any memory. It is safe to stop the | |
300 | * iteration at any moment and let the iterator go out of context. | |
301 | * | |
302 | * @param it | |
303 | * Device iterator handle. | |
304 | * | |
305 | * @param str | |
306 | * Device description string. | |
307 | * | |
308 | * @return | |
309 | * 0 on successful initialization. | |
310 | * <0 on error. | |
311 | */ | |
312 | __rte_experimental | |
313 | int | |
314 | rte_dev_iterator_init(struct rte_dev_iterator *it, const char *str); | |
315 | ||
316 | /** | |
317 | * Iterates on a device iterator. | |
318 | * | |
319 | * Generates a new rte_device handle corresponding to the next element | |
320 | * in the list described in comprehension by the iterator. | |
321 | * | |
322 | * The next object is returned, and the iterator is updated. | |
323 | * | |
324 | * @param it | |
325 | * Device iterator handle. | |
326 | * | |
327 | * @return | |
328 | * An rte_device handle if found. | |
329 | * NULL if an error occurred (rte_errno is set). | |
330 | * NULL if no device could be found (rte_errno is not set). | |
331 | */ | |
332 | __rte_experimental | |
333 | struct rte_device * | |
334 | rte_dev_iterator_next(struct rte_dev_iterator *it); | |
335 | ||
336 | #define RTE_DEV_FOREACH(dev, devstr, it) \ | |
337 | for (rte_dev_iterator_init(it, devstr), \ | |
338 | dev = rte_dev_iterator_next(it); \ | |
339 | dev != NULL; \ | |
340 | dev = rte_dev_iterator_next(it)) | |
341 | ||
342 | #ifdef __cplusplus | |
343 | } | |
344 | #endif | |
345 | ||
346 | /** | |
347 | * @warning | |
348 | * @b EXPERIMENTAL: this API may change without prior notice | |
349 | * | |
350 | * It registers the callback for the specific device. | |
351 | * Multiple callbacks cal be registered at the same time. | |
352 | * | |
353 | * @param device_name | |
354 | * The device name, that is the param name of the struct rte_device, | |
355 | * null value means for all devices. | |
356 | * @param cb_fn | |
357 | * callback address. | |
358 | * @param cb_arg | |
359 | * address of parameter for callback. | |
360 | * | |
361 | * @return | |
362 | * - On success, zero. | |
363 | * - On failure, a negative value. | |
364 | */ | |
365 | int __rte_experimental | |
366 | rte_dev_event_callback_register(const char *device_name, | |
367 | rte_dev_event_cb_fn cb_fn, | |
368 | void *cb_arg); | |
369 | ||
370 | /** | |
371 | * @warning | |
372 | * @b EXPERIMENTAL: this API may change without prior notice | |
373 | * | |
374 | * It unregisters the callback according to the specified device. | |
375 | * | |
376 | * @param device_name | |
377 | * The device name, that is the param name of the struct rte_device, | |
378 | * null value means for all devices and their callbacks. | |
379 | * @param cb_fn | |
380 | * callback address. | |
381 | * @param cb_arg | |
382 | * address of parameter for callback, (void *)-1 means to remove all | |
383 | * registered which has the same callback address. | |
384 | * | |
385 | * @return | |
386 | * - On success, return the number of callback entities removed. | |
387 | * - On failure, a negative value. | |
388 | */ | |
389 | int __rte_experimental | |
390 | rte_dev_event_callback_unregister(const char *device_name, | |
391 | rte_dev_event_cb_fn cb_fn, | |
392 | void *cb_arg); | |
393 | ||
9f95a23c TL |
394 | /** |
395 | * @warning | |
396 | * @b EXPERIMENTAL: this API may change without prior notice | |
397 | * | |
398 | * Executes all the user application registered callbacks for | |
399 | * the specific device. | |
400 | * | |
401 | * @param device_name | |
402 | * The device name. | |
403 | * @param event | |
404 | * the device event type. | |
405 | */ | |
406 | void __rte_experimental | |
407 | rte_dev_event_callback_process(const char *device_name, | |
408 | enum rte_dev_event_type event); | |
409 | ||
11fdf7f2 TL |
410 | /** |
411 | * @warning | |
412 | * @b EXPERIMENTAL: this API may change without prior notice | |
413 | * | |
414 | * Start the device event monitoring. | |
415 | * | |
416 | * @return | |
417 | * - On success, zero. | |
418 | * - On failure, a negative value. | |
419 | */ | |
420 | int __rte_experimental | |
421 | rte_dev_event_monitor_start(void); | |
422 | ||
423 | /** | |
424 | * @warning | |
425 | * @b EXPERIMENTAL: this API may change without prior notice | |
426 | * | |
427 | * Stop the device event monitoring. | |
428 | * | |
429 | * @return | |
430 | * - On success, zero. | |
431 | * - On failure, a negative value. | |
432 | */ | |
433 | int __rte_experimental | |
434 | rte_dev_event_monitor_stop(void); | |
435 | ||
9f95a23c TL |
436 | /** |
437 | * @warning | |
438 | * @b EXPERIMENTAL: this API may change without prior notice | |
439 | * | |
440 | * Enable hotplug handling for devices. | |
441 | * | |
442 | * @return | |
443 | * - On success, zero. | |
444 | * - On failure, a negative value. | |
445 | */ | |
446 | int __rte_experimental | |
447 | rte_dev_hotplug_handle_enable(void); | |
448 | ||
449 | /** | |
450 | * @warning | |
451 | * @b EXPERIMENTAL: this API may change without prior notice | |
452 | * | |
453 | * Disable hotplug handling for devices. | |
454 | * | |
455 | * @return | |
456 | * - On success, zero. | |
457 | * - On failure, a negative value. | |
458 | */ | |
459 | int __rte_experimental | |
460 | rte_dev_hotplug_handle_disable(void); | |
461 | ||
462 | /** | |
463 | * Device level DMA map function. | |
464 | * After a successful call, the memory segment will be mapped to the | |
465 | * given device. | |
466 | * | |
467 | * @note: Memory must be registered in advance using rte_extmem_* APIs. | |
468 | * | |
469 | * @param dev | |
470 | * Device pointer. | |
471 | * @param addr | |
472 | * Virtual address to map. | |
473 | * @param iova | |
474 | * IOVA address to map. | |
475 | * @param len | |
476 | * Length of the memory segment being mapped. | |
477 | * | |
478 | * @return | |
479 | * 0 if mapping was successful. | |
480 | * Negative value and rte_errno is set otherwise. | |
481 | */ | |
482 | int __rte_experimental | |
483 | rte_dev_dma_map(struct rte_device *dev, void *addr, uint64_t iova, size_t len); | |
484 | ||
485 | /** | |
486 | * Device level DMA unmap function. | |
487 | * After a successful call, the memory segment will no longer be | |
488 | * accessible by the given device. | |
489 | * | |
490 | * @note: Memory must be registered in advance using rte_extmem_* APIs. | |
491 | * | |
492 | * @param dev | |
493 | * Device pointer. | |
494 | * @param addr | |
495 | * Virtual address to unmap. | |
496 | * @param iova | |
497 | * IOVA address to unmap. | |
498 | * @param len | |
499 | * Length of the memory segment being mapped. | |
500 | * | |
501 | * @return | |
502 | * 0 if un-mapping was successful. | |
503 | * Negative value and rte_errno is set otherwise. | |
504 | */ | |
505 | int __rte_experimental | |
506 | rte_dev_dma_unmap(struct rte_device *dev, void *addr, uint64_t iova, | |
507 | size_t len); | |
508 | ||
11fdf7f2 | 509 | #endif /* _RTE_DEV_H_ */ |