1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(c) 2017 Intel Corporation. 3 * All rights reserved. 4 */ 5 6 #ifndef _RTE_EVENT_ETH_RX_ADAPTER_ 7 #define _RTE_EVENT_ETH_RX_ADAPTER_ 8 9 /** 10 * @file 11 * 12 * RTE Event Ethernet Rx Adapter 13 * 14 * An eventdev-based packet processing application enqueues/dequeues mbufs 15 * to/from the event device. Packet flow from the ethernet device to the event 16 * device can be accomplished using either HW or SW mechanisms depending on the 17 * platform and the particular combination of ethernet and event devices. The 18 * event ethernet Rx adapter provides common APIs to configure the packet flow 19 * from the ethernet devices to event devices across both these transfer 20 * mechanisms. 21 * 22 * The adapter uses a EAL service core function for SW based packet transfer 23 * and uses the eventdev PMD functions to configure HW based packet transfer 24 * between the ethernet device and the event device. For SW based packet 25 * transfer, if the mbuf does not have a timestamp set, the adapter adds a 26 * timestamp to the mbuf using rte_get_tsc_cycles(), this provides a more 27 * accurate timestamp as compared to if the application were to set the time 28 * stamp since it avoids event device schedule latency. 29 * 30 * The ethernet Rx event adapter's functions are: 31 * - rte_event_eth_rx_adapter_create_ext() 32 * - rte_event_eth_rx_adapter_create() 33 * - rte_event_eth_rx_adapter_free() 34 * - rte_event_eth_rx_adapter_queue_add() 35 * - rte_event_eth_rx_adapter_queue_del() 36 * - rte_event_eth_rx_adapter_start() 37 * - rte_event_eth_rx_adapter_stop() 38 * - rte_event_eth_rx_adapter_stats_get() 39 * - rte_event_eth_rx_adapter_stats_reset() 40 * 41 * The application creates an ethernet to event adapter using 42 * rte_event_eth_rx_adapter_create_ext() or rte_event_eth_rx_adapter_create() 43 * functions. 44 * The adapter needs to know which ethernet rx queues to poll for mbufs as well 45 * as event device parameters such as the event queue identifier, event 46 * priority and scheduling type that the adapter should use when constructing 47 * events. The rte_event_eth_rx_adapter_queue_add() function is provided for 48 * this purpose. 49 * The servicing weight parameter in the rte_event_eth_rx_adapter_queue_conf 50 * is applicable when the Rx adapter uses a service core function and is 51 * intended to provide application control of the frequency of polling ethernet 52 * device receive queues, for example, the application may want to poll higher 53 * priority queues with a higher frequency but at the same time not starve 54 * lower priority queues completely. If this parameter is zero and the receive 55 * interrupt is enabled when configuring the device, the receive queue is 56 * interrupt driven; else, the queue is assigned a servicing weight of one. 57 * 58 * The application can start/stop the adapter using the 59 * rte_event_eth_rx_adapter_start() and the rte_event_eth_rx_adapter_stop() 60 * functions. If the adapter uses a rte_service function, then the application 61 * is also required to assign a core to the service function and control the 62 * service core using the rte_service APIs. The 63 * rte_event_eth_rx_adapter_service_id_get() function can be used to retrieve 64 * the service function ID of the adapter in this case. 65 * 66 * For SW based packet transfers, i.e., when the 67 * RTE_EVENT_ETH_RX_ADAPTER_CAP_INTERNAL_PORT is not set in the adapter's 68 * capabilities flags for a particular ethernet device, the service function 69 * temporarily enqueues mbufs to an event buffer before batch enqueuing these 70 * to the event device. If the buffer fills up, the service function stops 71 * dequeuing packets from the ethernet device. The application may want to 72 * monitor the buffer fill level and instruct the service function to 73 * selectively buffer packets. The application may also use some other 74 * criteria to decide which packets should enter the event device even when 75 * the event buffer fill level is low. The 76 * rte_event_eth_rx_adapter_cb_register() function allows the 77 * application to register a callback that selects which packets to enqueue 78 * to the event device. 79 */ 80 81 #ifdef __cplusplus 82 extern "C" { 83 #endif 84 85 #include <stdint.h> 86 87 #include <rte_service.h> 88 89 #include "rte_eventdev.h" 90 91 #define RTE_EVENT_ETH_RX_ADAPTER_MAX_INSTANCE 32 92 93 /* struct rte_event_eth_rx_adapter_queue_conf flags definitions */ 94 #define RTE_EVENT_ETH_RX_ADAPTER_QUEUE_FLOW_ID_VALID 0x1 95 /**< This flag indicates the flow identifier is valid 96 * @see rte_event_eth_rx_adapter_queue_conf::rx_queue_flags 97 */ 98 99 /** 100 * @warning 101 * @b EXPERIMENTAL: this API may change without prior notice 102 * 103 * Adapter configuration structure that the adapter configuration callback 104 * function is expected to fill out 105 * @see rte_event_eth_rx_adapter_conf_cb 106 */ 107 struct rte_event_eth_rx_adapter_conf { 108 uint8_t event_port_id; 109 /**< Event port identifier, the adapter enqueues mbuf events to this 110 * port. 111 */ 112 uint32_t max_nb_rx; 113 /**< The adapter can return early if it has processed at least 114 * max_nb_rx mbufs. This isn't treated as a requirement; batching may 115 * cause the adapter to process more than max_nb_rx mbufs. 116 */ 117 }; 118 119 /** 120 * @warning 121 * @b EXPERIMENTAL: this API may change without prior notice 122 * 123 * Function type used for adapter configuration callback. The callback is 124 * used to fill in members of the struct rte_event_eth_rx_adapter_conf, this 125 * callback is invoked when creating a SW service for packet transfer from 126 * ethdev queues to the event device. The SW service is created within the 127 * rte_event_eth_rx_adapter_queue_add() function if SW based packet transfers 128 * from ethdev queues to the event device are required. 129 * 130 * @param id 131 * Adapter identifier. 132 * 133 * @param dev_id 134 * Event device identifier. 135 * 136 * @param [out] conf 137 * Structure that needs to be populated by this callback. 138 * 139 * @param arg 140 * Argument to the callback. This is the same as the conf_arg passed to the 141 * rte_event_eth_rx_adapter_create_ext(). 142 */ 143 typedef int (*rte_event_eth_rx_adapter_conf_cb) (uint8_t id, uint8_t dev_id, 144 struct rte_event_eth_rx_adapter_conf *conf, 145 void *arg); 146 147 /** 148 * @warning 149 * @b EXPERIMENTAL: this API may change without prior notice 150 * 151 * Rx queue configuration structure 152 */ 153 struct rte_event_eth_rx_adapter_queue_conf { 154 uint32_t rx_queue_flags; 155 /**< Flags for handling received packets 156 * @see RTE_EVENT_ETH_RX_ADAPTER_QUEUE_FLOW_ID_VALID 157 */ 158 uint16_t servicing_weight; 159 /**< Relative polling frequency of ethernet receive queue when the 160 * adapter uses a service core function for ethernet to event device 161 * transfers. If it is set to zero, the Rx queue is interrupt driven 162 * (unless rx queue interrupts are not enabled for the ethernet 163 * device). 164 */ 165 struct rte_event ev; 166 /**< 167 * The values from the following event fields will be used when 168 * queuing mbuf events: 169 * - event_queue_id: Targeted event queue ID for received packets. 170 * - event_priority: Event priority of packets from this Rx queue in 171 * the event queue relative to other events. 172 * - sched_type: Scheduling type for packets from this Rx queue. 173 * - flow_id: If the RTE_ETH_RX_EVENT_ADAPTER_QUEUE_FLOW_ID_VALID bit 174 * is set in rx_queue_flags, this flow_id is used for all 175 * packets received from this queue. Otherwise the flow ID 176 * is set to the RSS hash of the src and dst IPv4/6 177 * addresses. 178 * 179 * The event adapter sets ev.event_type to RTE_EVENT_TYPE_ETHDEV in the 180 * enqueued event. 181 */ 182 }; 183 184 /** 185 * @warning 186 * @b EXPERIMENTAL: this API may change without prior notice 187 * 188 * A structure used to retrieve statistics for an eth rx adapter instance. 189 */ 190 struct rte_event_eth_rx_adapter_stats { 191 uint64_t rx_poll_count; 192 /**< Receive queue poll count */ 193 uint64_t rx_packets; 194 /**< Received packet count */ 195 uint64_t rx_enq_count; 196 /**< Eventdev enqueue count */ 197 uint64_t rx_enq_retry; 198 /**< Eventdev enqueue retry count */ 199 uint64_t rx_enq_start_ts; 200 /**< Rx enqueue start timestamp */ 201 uint64_t rx_enq_block_cycles; 202 /**< Cycles for which the service is blocked by the event device, 203 * i.e, the service fails to enqueue to the event device. 204 */ 205 uint64_t rx_enq_end_ts; 206 /**< Latest timestamp at which the service is unblocked 207 * by the event device. The start, end timestamps and 208 * block cycles can be used to compute the percentage of 209 * cycles the service is blocked by the event device. 210 */ 211 uint64_t rx_intr_packets; 212 /**< Received packet count for interrupt mode Rx queues */ 213 }; 214 215 /** 216 * @warning 217 * @b EXPERIMENTAL: this API may change without prior notice 218 * 219 * Callback function invoked by the SW adapter before it continues 220 * to process packets. The callback is passed the size of the enqueue 221 * buffer in the SW adapter and the occupancy of the buffer. The 222 * callback can use these values to decide which mbufs should be 223 * enqueued to the event device. If the return value of the callback 224 * is less than nb_mbuf then the SW adapter uses the return value to 225 * enqueue enq_mbuf[] to the event device. 226 * 227 * @param eth_dev_id 228 * Port identifier of the Ethernet device. 229 * @param queue_id 230 * Receive queue index. 231 * @param enqueue_buf_size 232 * Total enqueue buffer size. 233 * @param enqueue_buf_count 234 * mbuf count in enqueue buffer. 235 * @param mbuf 236 * mbuf array. 237 * @param nb_mbuf 238 * mbuf count. 239 * @param cb_arg 240 * Callback argument. 241 * @param[out] enq_mbuf 242 * The adapter enqueues enq_mbuf[] if the return value of the 243 * callback is less than nb_mbuf 244 * @return 245 * Returns the number of mbufs should be enqueued to eventdev 246 */ 247 typedef uint16_t (*rte_event_eth_rx_adapter_cb_fn)(uint16_t eth_dev_id, 248 uint16_t queue_id, 249 uint32_t enqueue_buf_size, 250 uint32_t enqueue_buf_count, 251 struct rte_mbuf **mbuf, 252 uint16_t nb_mbuf, 253 void *cb_arg, 254 struct rte_mbuf **enq_buf); 255 256 /** 257 * @warning 258 * @b EXPERIMENTAL: this API may change without prior notice 259 * 260 * Create a new ethernet Rx event adapter with the specified identifier. 261 * 262 * @param id 263 * The identifier of the ethernet Rx event adapter. 264 * 265 * @param dev_id 266 * The identifier of the device to configure. 267 * 268 * @param conf_cb 269 * Callback function that fills in members of a 270 * struct rte_event_eth_rx_adapter_conf struct passed into 271 * it. 272 * 273 * @param conf_arg 274 * Argument that is passed to the conf_cb function. 275 * 276 * @return 277 * - 0: Success 278 * - <0: Error code on failure 279 */ 280 int rte_event_eth_rx_adapter_create_ext(uint8_t id, uint8_t dev_id, 281 rte_event_eth_rx_adapter_conf_cb conf_cb, 282 void *conf_arg); 283 284 /** 285 * @warning 286 * @b EXPERIMENTAL: this API may change without prior notice 287 * 288 * Create a new ethernet Rx event adapter with the specified identifier. 289 * This function uses an internal configuration function that creates an event 290 * port. This default function reconfigures the event device with an 291 * additional event port and setups up the event port using the port_config 292 * parameter passed into this function. In case the application needs more 293 * control in configuration of the service, it should use the 294 * rte_event_eth_rx_adapter_create_ext() version. 295 * 296 * @param id 297 * The identifier of the ethernet Rx event adapter. 298 * 299 * @param dev_id 300 * The identifier of the device to configure. 301 * 302 * @param port_config 303 * Argument of type *rte_event_port_conf* that is passed to the conf_cb 304 * function. 305 * 306 * @return 307 * - 0: Success 308 * - <0: Error code on failure 309 */ 310 int rte_event_eth_rx_adapter_create(uint8_t id, uint8_t dev_id, 311 struct rte_event_port_conf *port_config); 312 313 /** 314 * @warning 315 * @b EXPERIMENTAL: this API may change without prior notice 316 * 317 * Free an event adapter 318 * 319 * @param id 320 * Adapter identifier. 321 * 322 * @return 323 * - 0: Success 324 * - <0: Error code on failure, If the adapter still has Rx queues 325 * added to it, the function returns -EBUSY. 326 */ 327 int rte_event_eth_rx_adapter_free(uint8_t id); 328 329 /** 330 * @warning 331 * @b EXPERIMENTAL: this API may change without prior notice 332 * 333 * Add receive queue to an event adapter. After a queue has been 334 * added to the event adapter, the result of the application calling 335 * rte_eth_rx_burst(eth_dev_id, rx_queue_id, ..) is undefined. 336 * 337 * @param id 338 * Adapter identifier. 339 * 340 * @param eth_dev_id 341 * Port identifier of Ethernet device. 342 * 343 * @param rx_queue_id 344 * Ethernet device receive queue index. 345 * If rx_queue_id is -1, then all Rx queues configured for 346 * the device are added. If the ethdev Rx queues can only be 347 * connected to a single event queue then rx_queue_id is 348 * required to be -1. 349 * @see RTE_EVENT_ETH_RX_ADAPTER_CAP_MULTI_EVENTQ 350 * 351 * @param conf 352 * Additional configuration structure of type *rte_event_eth_rx_adapter_conf* 353 * 354 * @return 355 * - 0: Success, Receive queue added correctly. 356 * - <0: Error code on failure. 357 * - (-EIO) device reconfiguration and restart error. The adapter reconfigures 358 * the event device with an additional port if it is required to use a service 359 * function for packet transfer from the ethernet device to the event device. 360 * If the device had been started before this call, this error code indicates 361 * an error in restart following an error in reconfiguration, i.e., a 362 * combination of the two error codes. 363 */ 364 int rte_event_eth_rx_adapter_queue_add(uint8_t id, 365 uint16_t eth_dev_id, 366 int32_t rx_queue_id, 367 const struct rte_event_eth_rx_adapter_queue_conf *conf); 368 369 /** 370 * @warning 371 * @b EXPERIMENTAL: this API may change without prior notice 372 * 373 * Delete receive queue from an event adapter. 374 * 375 * @param id 376 * Adapter identifier. 377 * 378 * @param eth_dev_id 379 * Port identifier of Ethernet device. 380 * 381 * @param rx_queue_id 382 * Ethernet device receive queue index. 383 * If rx_queue_id is -1, then all Rx queues configured for 384 * the device are deleted. If the ethdev Rx queues can only be 385 * connected to a single event queue then rx_queue_id is 386 * required to be -1. 387 * @see RTE_EVENT_ETH_RX_ADAPTER_CAP_MULTI_EVENTQ 388 * 389 * @return 390 * - 0: Success, Receive queue deleted correctly. 391 * - <0: Error code on failure. 392 */ 393 int rte_event_eth_rx_adapter_queue_del(uint8_t id, uint16_t eth_dev_id, 394 int32_t rx_queue_id); 395 396 /** 397 * @warning 398 * @b EXPERIMENTAL: this API may change without prior notice 399 * 400 * Start ethernet Rx event adapter 401 * 402 * @param id 403 * Adapter identifier. 404 * 405 * @return 406 * - 0: Success, Adapter started correctly. 407 * - <0: Error code on failure. 408 */ 409 int rte_event_eth_rx_adapter_start(uint8_t id); 410 411 /** 412 * @warning 413 * @b EXPERIMENTAL: this API may change without prior notice 414 * 415 * Stop ethernet Rx event adapter 416 * 417 * @param id 418 * Adapter identifier. 419 * 420 * @return 421 * - 0: Success, Adapter started correctly. 422 * - <0: Error code on failure. 423 */ 424 int rte_event_eth_rx_adapter_stop(uint8_t id); 425 426 /** 427 * @warning 428 * @b EXPERIMENTAL: this API may change without prior notice 429 * 430 * Retrieve statistics for an adapter 431 * 432 * @param id 433 * Adapter identifier. 434 * 435 * @param [out] stats 436 * A pointer to structure used to retrieve statistics for an adapter. 437 * 438 * @return 439 * - 0: Success, retrieved successfully. 440 * - <0: Error code on failure. 441 */ 442 int rte_event_eth_rx_adapter_stats_get(uint8_t id, 443 struct rte_event_eth_rx_adapter_stats *stats); 444 445 /** 446 * @warning 447 * @b EXPERIMENTAL: this API may change without prior notice 448 * 449 * Reset statistics for an adapter. 450 * 451 * @param id 452 * Adapter identifier. 453 * 454 * @return 455 * - 0: Success, statistics reset successfully. 456 * - <0: Error code on failure. 457 */ 458 int rte_event_eth_rx_adapter_stats_reset(uint8_t id); 459 460 /** 461 * @warning 462 * @b EXPERIMENTAL: this API may change without prior notice 463 * 464 * Retrieve the service ID of an adapter. If the adapter doesn't use 465 * a rte_service function, this function returns -ESRCH. 466 * 467 * @param id 468 * Adapter identifier. 469 * 470 * @param [out] service_id 471 * A pointer to a uint32_t, to be filled in with the service id. 472 * 473 * @return 474 * - 0: Success 475 * - <0: Error code on failure, if the adapter doesn't use a rte_service 476 * function, this function returns -ESRCH. 477 */ 478 int rte_event_eth_rx_adapter_service_id_get(uint8_t id, uint32_t *service_id); 479 480 /** 481 * @warning 482 * @b EXPERIMENTAL: this API may change without prior notice 483 * 484 * Register callback to process Rx packets, this is supported for 485 * SW based packet transfers. 486 * @see rte_event_eth_rx_cb_fn 487 * 488 * @param id 489 * Adapter identifier. 490 * @param eth_dev_id 491 * Port identifier of Ethernet device. 492 * @param cb_fn 493 * Callback function. 494 * @param cb_arg 495 * Callback arg. 496 * @return 497 * - 0: Success 498 * - <0: Error code on failure. 499 */ 500 int __rte_experimental 501 rte_event_eth_rx_adapter_cb_register(uint8_t id, 502 uint16_t eth_dev_id, 503 rte_event_eth_rx_adapter_cb_fn cb_fn, 504 void *cb_arg); 505 506 #ifdef __cplusplus 507 } 508 #endif 509 #endif /* _RTE_EVENT_ETH_RX_ADAPTER_ */ 510