5c71ba763424a7a86f8347362604027de8aef0be
[dpdk.git] / test / test / virtual_pmd.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(c) 2010-2014 Intel Corporation
3  */
4
5 #include <rte_mbuf.h>
6 #include <rte_ethdev.h>
7 #include <rte_pci.h>
8 #include <rte_bus_pci.h>
9 #include <rte_malloc.h>
10 #include <rte_memcpy.h>
11 #include <rte_memory.h>
12 #include <rte_ring.h>
13
14 #include "virtual_pmd.h"
15
16 #define MAX_PKT_BURST 512
17
18 static const char *virtual_ethdev_driver_name = "Virtual PMD";
19
20 struct virtual_ethdev_private {
21         struct eth_dev_ops dev_ops;
22         struct rte_eth_stats eth_stats;
23
24         struct rte_ring *rx_queue;
25         struct rte_ring *tx_queue;
26
27         int tx_burst_fail_count;
28 };
29
30 struct virtual_ethdev_queue {
31         int port_id;
32         int queue_id;
33 };
34
35 static int
36 virtual_ethdev_start_success(struct rte_eth_dev *eth_dev __rte_unused)
37 {
38         eth_dev->data->dev_started = 1;
39
40         return 0;
41 }
42
43 static int
44 virtual_ethdev_start_fail(struct rte_eth_dev *eth_dev __rte_unused)
45 {
46         eth_dev->data->dev_started = 0;
47
48         return -1;
49 }
50 static void  virtual_ethdev_stop(struct rte_eth_dev *eth_dev __rte_unused)
51 {
52         void *pkt = NULL;
53         struct virtual_ethdev_private *prv = eth_dev->data->dev_private;
54
55         eth_dev->data->dev_link.link_status = ETH_LINK_DOWN;
56         eth_dev->data->dev_started = 0;
57         while (rte_ring_dequeue(prv->rx_queue, &pkt) != -ENOENT)
58                 rte_pktmbuf_free(pkt);
59
60         while (rte_ring_dequeue(prv->tx_queue, &pkt) != -ENOENT)
61                 rte_pktmbuf_free(pkt);
62 }
63
64 static void
65 virtual_ethdev_close(struct rte_eth_dev *dev __rte_unused)
66 {}
67
68 static int
69 virtual_ethdev_configure_success(struct rte_eth_dev *dev __rte_unused)
70 {
71         return 0;
72 }
73
74 static int
75 virtual_ethdev_configure_fail(struct rte_eth_dev *dev __rte_unused)
76 {
77         return -1;
78 }
79
80 static void
81 virtual_ethdev_info_get(struct rte_eth_dev *dev __rte_unused,
82                 struct rte_eth_dev_info *dev_info)
83 {
84         dev_info->driver_name = virtual_ethdev_driver_name;
85         dev_info->max_mac_addrs = 1;
86
87         dev_info->max_rx_pktlen = (uint32_t)2048;
88
89         dev_info->max_rx_queues = (uint16_t)128;
90         dev_info->max_tx_queues = (uint16_t)512;
91
92         dev_info->min_rx_bufsize = 0;
93 }
94
95 static int
96 virtual_ethdev_rx_queue_setup_success(struct rte_eth_dev *dev,
97                 uint16_t rx_queue_id, uint16_t nb_rx_desc __rte_unused,
98                 unsigned int socket_id,
99                 const struct rte_eth_rxconf *rx_conf __rte_unused,
100                 struct rte_mempool *mb_pool __rte_unused)
101 {
102         struct virtual_ethdev_queue *rx_q;
103
104         rx_q = (struct virtual_ethdev_queue *)rte_zmalloc_socket(NULL,
105                         sizeof(struct virtual_ethdev_queue), 0, socket_id);
106
107         if (rx_q == NULL)
108                 return -1;
109
110         rx_q->port_id = dev->data->port_id;
111         rx_q->queue_id = rx_queue_id;
112
113         dev->data->rx_queues[rx_queue_id] = rx_q;
114
115         return 0;
116 }
117
118 static int
119 virtual_ethdev_rx_queue_setup_fail(struct rte_eth_dev *dev __rte_unused,
120                 uint16_t rx_queue_id __rte_unused, uint16_t nb_rx_desc __rte_unused,
121                 unsigned int socket_id __rte_unused,
122                 const struct rte_eth_rxconf *rx_conf __rte_unused,
123                 struct rte_mempool *mb_pool __rte_unused)
124 {
125         return -1;
126 }
127
128 static int
129 virtual_ethdev_tx_queue_setup_success(struct rte_eth_dev *dev,
130                 uint16_t tx_queue_id, uint16_t nb_tx_desc __rte_unused,
131                 unsigned int socket_id,
132                 const struct rte_eth_txconf *tx_conf __rte_unused)
133 {
134         struct virtual_ethdev_queue *tx_q;
135
136         tx_q = (struct virtual_ethdev_queue *)rte_zmalloc_socket(NULL,
137                         sizeof(struct virtual_ethdev_queue), 0, socket_id);
138
139         if (tx_q == NULL)
140                 return -1;
141
142         tx_q->port_id = dev->data->port_id;
143         tx_q->queue_id = tx_queue_id;
144
145         dev->data->tx_queues[tx_queue_id] = tx_q;
146
147         return 0;
148 }
149
150 static int
151 virtual_ethdev_tx_queue_setup_fail(struct rte_eth_dev *dev __rte_unused,
152                 uint16_t tx_queue_id __rte_unused, uint16_t nb_tx_desc __rte_unused,
153                 unsigned int socket_id __rte_unused,
154                 const struct rte_eth_txconf *tx_conf __rte_unused)
155 {
156         return -1;
157 }
158
159 static void
160 virtual_ethdev_rx_queue_release(void *q __rte_unused)
161 {
162 }
163
164 static void
165 virtual_ethdev_tx_queue_release(void *q __rte_unused)
166 {
167 }
168
169 static int
170 virtual_ethdev_link_update_success(struct rte_eth_dev *bonded_eth_dev,
171                 int wait_to_complete __rte_unused)
172 {
173         if (!bonded_eth_dev->data->dev_started)
174                 bonded_eth_dev->data->dev_link.link_status = ETH_LINK_DOWN;
175
176         return 0;
177 }
178
179 static int
180 virtual_ethdev_link_update_fail(struct rte_eth_dev *bonded_eth_dev __rte_unused,
181                 int wait_to_complete __rte_unused)
182 {
183         return -1;
184 }
185
186 static int
187 virtual_ethdev_stats_get(struct rte_eth_dev *dev, struct rte_eth_stats *stats)
188 {
189         struct virtual_ethdev_private *dev_private = dev->data->dev_private;
190
191         if (stats)
192                 rte_memcpy(stats, &dev_private->eth_stats, sizeof(*stats));
193
194         return 0;
195 }
196
197 static void
198 virtual_ethdev_stats_reset(struct rte_eth_dev *dev)
199 {
200         struct virtual_ethdev_private *dev_private = dev->data->dev_private;
201         void *pkt = NULL;
202
203         while (rte_ring_dequeue(dev_private->tx_queue, &pkt) == -ENOBUFS)
204                         rte_pktmbuf_free(pkt);
205
206         /* Reset internal statistics */
207         memset(&dev_private->eth_stats, 0, sizeof(dev_private->eth_stats));
208 }
209
210 static void
211 virtual_ethdev_promiscuous_mode_enable(struct rte_eth_dev *dev __rte_unused)
212 {}
213
214 static void
215 virtual_ethdev_promiscuous_mode_disable(struct rte_eth_dev *dev __rte_unused)
216 {}
217
218
219 static const struct eth_dev_ops virtual_ethdev_default_dev_ops = {
220         .dev_configure = virtual_ethdev_configure_success,
221         .dev_start = virtual_ethdev_start_success,
222         .dev_stop = virtual_ethdev_stop,
223         .dev_close = virtual_ethdev_close,
224         .dev_infos_get = virtual_ethdev_info_get,
225         .rx_queue_setup = virtual_ethdev_rx_queue_setup_success,
226         .tx_queue_setup = virtual_ethdev_tx_queue_setup_success,
227         .rx_queue_release = virtual_ethdev_rx_queue_release,
228         .tx_queue_release = virtual_ethdev_tx_queue_release,
229         .link_update = virtual_ethdev_link_update_success,
230         .stats_get = virtual_ethdev_stats_get,
231         .stats_reset = virtual_ethdev_stats_reset,
232         .promiscuous_enable = virtual_ethdev_promiscuous_mode_enable,
233         .promiscuous_disable = virtual_ethdev_promiscuous_mode_disable
234 };
235
236
237 void
238 virtual_ethdev_start_fn_set_success(uint16_t port_id, uint8_t success)
239 {
240         struct rte_eth_dev *dev = &rte_eth_devices[port_id];
241         struct virtual_ethdev_private *dev_private = dev->data->dev_private;
242         struct eth_dev_ops *dev_ops = &dev_private->dev_ops;
243
244         if (success)
245                 dev_ops->dev_start = virtual_ethdev_start_success;
246         else
247                 dev_ops->dev_start = virtual_ethdev_start_fail;
248
249 }
250
251 void
252 virtual_ethdev_configure_fn_set_success(uint16_t port_id, uint8_t success)
253 {
254         struct rte_eth_dev *dev = &rte_eth_devices[port_id];
255         struct virtual_ethdev_private *dev_private = dev->data->dev_private;
256         struct eth_dev_ops *dev_ops = &dev_private->dev_ops;
257
258         if (success)
259                 dev_ops->dev_configure = virtual_ethdev_configure_success;
260         else
261                 dev_ops->dev_configure = virtual_ethdev_configure_fail;
262 }
263
264 void
265 virtual_ethdev_rx_queue_setup_fn_set_success(uint16_t port_id, uint8_t success)
266 {
267         struct rte_eth_dev *dev = &rte_eth_devices[port_id];
268         struct virtual_ethdev_private *dev_private = dev->data->dev_private;
269         struct eth_dev_ops *dev_ops = &dev_private->dev_ops;
270
271         if (success)
272                 dev_ops->rx_queue_setup = virtual_ethdev_rx_queue_setup_success;
273         else
274                 dev_ops->rx_queue_setup = virtual_ethdev_rx_queue_setup_fail;
275 }
276
277 void
278 virtual_ethdev_tx_queue_setup_fn_set_success(uint16_t port_id, uint8_t success)
279 {
280         struct rte_eth_dev *dev = &rte_eth_devices[port_id];
281         struct virtual_ethdev_private *dev_private = dev->data->dev_private;
282         struct eth_dev_ops *dev_ops = &dev_private->dev_ops;
283
284         if (success)
285                 dev_ops->tx_queue_setup = virtual_ethdev_tx_queue_setup_success;
286         else
287                 dev_ops->tx_queue_setup = virtual_ethdev_tx_queue_setup_fail;
288 }
289
290 void
291 virtual_ethdev_link_update_fn_set_success(uint16_t port_id, uint8_t success)
292 {
293         struct rte_eth_dev *dev = &rte_eth_devices[port_id];
294         struct virtual_ethdev_private *dev_private = dev->data->dev_private;
295         struct eth_dev_ops *dev_ops = &dev_private->dev_ops;
296
297         if (success)
298                 dev_ops->link_update = virtual_ethdev_link_update_success;
299         else
300                 dev_ops->link_update = virtual_ethdev_link_update_fail;
301 }
302
303
304 static uint16_t
305 virtual_ethdev_rx_burst_success(void *queue __rte_unused,
306                                                          struct rte_mbuf **bufs,
307                                                          uint16_t nb_pkts)
308 {
309         struct rte_eth_dev *vrtl_eth_dev;
310         struct virtual_ethdev_queue *pq_map;
311         struct virtual_ethdev_private *dev_private;
312
313         int rx_count, i;
314
315         pq_map = (struct virtual_ethdev_queue *)queue;
316         vrtl_eth_dev = &rte_eth_devices[pq_map->port_id];
317         dev_private = vrtl_eth_dev->data->dev_private;
318
319         rx_count = rte_ring_dequeue_burst(dev_private->rx_queue, (void **) bufs,
320                         nb_pkts, NULL);
321
322         /* increments ipackets count */
323         dev_private->eth_stats.ipackets += rx_count;
324
325         /* increments ibytes count */
326         for (i = 0; i < rx_count; i++)
327                 dev_private->eth_stats.ibytes += rte_pktmbuf_pkt_len(bufs[i]);
328
329         return rx_count;
330 }
331
332 static uint16_t
333 virtual_ethdev_rx_burst_fail(void *queue __rte_unused,
334                                                          struct rte_mbuf **bufs __rte_unused,
335                                                          uint16_t nb_pkts __rte_unused)
336 {
337         return 0;
338 }
339
340 static uint16_t
341 virtual_ethdev_tx_burst_success(void *queue, struct rte_mbuf **bufs,
342                 uint16_t nb_pkts)
343 {
344         struct virtual_ethdev_queue *tx_q = queue;
345
346         struct rte_eth_dev *vrtl_eth_dev;
347         struct virtual_ethdev_private *dev_private;
348
349         int i;
350
351         vrtl_eth_dev = &rte_eth_devices[tx_q->port_id];
352         dev_private = vrtl_eth_dev->data->dev_private;
353
354         if (!vrtl_eth_dev->data->dev_link.link_status)
355                 nb_pkts = 0;
356         else
357                 nb_pkts = rte_ring_enqueue_burst(dev_private->tx_queue, (void **)bufs,
358                                 nb_pkts, NULL);
359
360         /* increment opacket count */
361         dev_private->eth_stats.opackets += nb_pkts;
362
363         /* increment obytes count */
364         for (i = 0; i < nb_pkts; i++)
365                 dev_private->eth_stats.obytes += rte_pktmbuf_pkt_len(bufs[i]);
366
367         return nb_pkts;
368 }
369
370 static uint16_t
371 virtual_ethdev_tx_burst_fail(void *queue, struct rte_mbuf **bufs,
372                 uint16_t nb_pkts)
373 {
374         struct rte_eth_dev *vrtl_eth_dev = NULL;
375         struct virtual_ethdev_queue *tx_q = NULL;
376         struct virtual_ethdev_private *dev_private = NULL;
377
378         int i;
379
380         tx_q = queue;
381         vrtl_eth_dev = &rte_eth_devices[tx_q->port_id];
382         dev_private = vrtl_eth_dev->data->dev_private;
383
384         if (dev_private->tx_burst_fail_count < nb_pkts) {
385                 int successfully_txd = nb_pkts - dev_private->tx_burst_fail_count;
386
387                 /* increment opacket count */
388                 dev_private->eth_stats.opackets += successfully_txd;
389
390                 /* free packets in burst */
391                 for (i = 0; i < successfully_txd; i++) {
392                         /* free packets in burst */
393                         if (bufs[i] != NULL)
394                                 rte_pktmbuf_free(bufs[i]);
395
396                         bufs[i] = NULL;
397                 }
398
399                 return successfully_txd;
400         }
401
402         return 0;
403 }
404
405
406 void
407 virtual_ethdev_rx_burst_fn_set_success(uint16_t port_id, uint8_t success)
408 {
409         struct rte_eth_dev *vrtl_eth_dev = &rte_eth_devices[port_id];
410
411         if (success)
412                 vrtl_eth_dev->rx_pkt_burst = virtual_ethdev_rx_burst_success;
413         else
414                 vrtl_eth_dev->rx_pkt_burst = virtual_ethdev_rx_burst_fail;
415 }
416
417
418 void
419 virtual_ethdev_tx_burst_fn_set_success(uint16_t port_id, uint8_t success)
420 {
421         struct virtual_ethdev_private *dev_private = NULL;
422         struct rte_eth_dev *vrtl_eth_dev = &rte_eth_devices[port_id];
423
424         dev_private = vrtl_eth_dev->data->dev_private;
425
426         if (success)
427                 vrtl_eth_dev->tx_pkt_burst = virtual_ethdev_tx_burst_success;
428         else
429                 vrtl_eth_dev->tx_pkt_burst = virtual_ethdev_tx_burst_fail;
430
431         dev_private->tx_burst_fail_count = 0;
432 }
433
434 void
435 virtual_ethdev_tx_burst_fn_set_tx_pkt_fail_count(uint16_t port_id,
436                 uint8_t packet_fail_count)
437 {
438         struct virtual_ethdev_private *dev_private = NULL;
439         struct rte_eth_dev *vrtl_eth_dev = &rte_eth_devices[port_id];
440
441
442         dev_private = vrtl_eth_dev->data->dev_private;
443         dev_private->tx_burst_fail_count = packet_fail_count;
444 }
445
446 void
447 virtual_ethdev_set_link_status(uint16_t port_id, uint8_t link_status)
448 {
449         struct rte_eth_dev *vrtl_eth_dev = &rte_eth_devices[port_id];
450
451         vrtl_eth_dev->data->dev_link.link_status = link_status;
452 }
453
454 void
455 virtual_ethdev_simulate_link_status_interrupt(uint16_t port_id,
456                 uint8_t link_status)
457 {
458         struct rte_eth_dev *vrtl_eth_dev = &rte_eth_devices[port_id];
459
460         vrtl_eth_dev->data->dev_link.link_status = link_status;
461
462         _rte_eth_dev_callback_process(vrtl_eth_dev, RTE_ETH_EVENT_INTR_LSC,
463                                       NULL, NULL);
464 }
465
466 int
467 virtual_ethdev_add_mbufs_to_rx_queue(uint16_t port_id,
468                 struct rte_mbuf **pkt_burst, int burst_length)
469 {
470         struct rte_eth_dev *vrtl_eth_dev = &rte_eth_devices[port_id];
471         struct virtual_ethdev_private *dev_private =
472                         vrtl_eth_dev->data->dev_private;
473
474         return rte_ring_enqueue_burst(dev_private->rx_queue, (void **)pkt_burst,
475                         burst_length, NULL);
476 }
477
478 int
479 virtual_ethdev_get_mbufs_from_tx_queue(uint16_t port_id,
480                 struct rte_mbuf **pkt_burst, int burst_length)
481 {
482         struct virtual_ethdev_private *dev_private;
483         struct rte_eth_dev *vrtl_eth_dev = &rte_eth_devices[port_id];
484
485         dev_private = vrtl_eth_dev->data->dev_private;
486         return rte_ring_dequeue_burst(dev_private->tx_queue, (void **)pkt_burst,
487                 burst_length, NULL);
488 }
489
490
491 int
492 virtual_ethdev_create(const char *name, struct ether_addr *mac_addr,
493                 uint8_t socket_id, uint8_t isr_support)
494 {
495         struct rte_pci_device *pci_dev = NULL;
496         struct rte_eth_dev *eth_dev = NULL;
497         struct rte_pci_driver *pci_drv = NULL;
498         struct rte_pci_id *id_table = NULL;
499         struct virtual_ethdev_private *dev_private = NULL;
500         char name_buf[RTE_RING_NAMESIZE];
501
502
503         /* now do all data allocation - for eth_dev structure, dummy pci driver
504          * and internal (dev_private) data
505          */
506
507         pci_dev = rte_zmalloc_socket(name, sizeof(*pci_dev), 0, socket_id);
508         if (pci_dev == NULL)
509                 goto err;
510
511         pci_drv = rte_zmalloc_socket(name, sizeof(*pci_drv), 0, socket_id);
512         if (pci_drv == NULL)
513                 goto err;
514
515         id_table = rte_zmalloc_socket(name, sizeof(*id_table), 0, socket_id);
516         if (id_table == NULL)
517                 goto err;
518         id_table->device_id = 0xBEEF;
519
520         dev_private = rte_zmalloc_socket(name, sizeof(*dev_private), 0, socket_id);
521         if (dev_private == NULL)
522                 goto err;
523
524         snprintf(name_buf, sizeof(name_buf), "%s_rxQ", name);
525         dev_private->rx_queue = rte_ring_create(name_buf, MAX_PKT_BURST, socket_id,
526                         0);
527         if (dev_private->rx_queue == NULL)
528                 goto err;
529
530         snprintf(name_buf, sizeof(name_buf), "%s_txQ", name);
531         dev_private->tx_queue = rte_ring_create(name_buf, MAX_PKT_BURST, socket_id,
532                         0);
533         if (dev_private->tx_queue == NULL)
534                 goto err;
535
536         /* reserve an ethdev entry */
537         eth_dev = rte_eth_dev_allocate(name);
538         if (eth_dev == NULL)
539                 goto err;
540
541         pci_dev->device.numa_node = socket_id;
542         pci_dev->device.name = eth_dev->data->name;
543         pci_drv->driver.name = virtual_ethdev_driver_name;
544         pci_drv->id_table = id_table;
545
546         if (isr_support)
547                 pci_drv->drv_flags |= RTE_PCI_DRV_INTR_LSC;
548         else
549                 pci_drv->drv_flags &= ~RTE_PCI_DRV_INTR_LSC;
550
551
552         eth_dev->device = &pci_dev->device;
553         eth_dev->device->driver = &pci_drv->driver;
554
555         eth_dev->data->nb_rx_queues = (uint16_t)1;
556         eth_dev->data->nb_tx_queues = (uint16_t)1;
557
558         eth_dev->data->dev_link.link_status = ETH_LINK_DOWN;
559         eth_dev->data->dev_link.link_speed = ETH_SPEED_NUM_10G;
560         eth_dev->data->dev_link.link_duplex = ETH_LINK_FULL_DUPLEX;
561
562         eth_dev->data->mac_addrs = rte_zmalloc(name, ETHER_ADDR_LEN, 0);
563         if (eth_dev->data->mac_addrs == NULL)
564                 goto err;
565
566         memcpy(eth_dev->data->mac_addrs, mac_addr,
567                         sizeof(*eth_dev->data->mac_addrs));
568
569         eth_dev->data->dev_started = 0;
570         eth_dev->data->promiscuous = 0;
571         eth_dev->data->scattered_rx = 0;
572         eth_dev->data->all_multicast = 0;
573
574         eth_dev->data->dev_private = dev_private;
575
576         /* Copy default device operation functions */
577         dev_private->dev_ops = virtual_ethdev_default_dev_ops;
578         eth_dev->dev_ops = &dev_private->dev_ops;
579
580         pci_dev->device.driver = &pci_drv->driver;
581         eth_dev->device = &pci_dev->device;
582
583         eth_dev->rx_pkt_burst = virtual_ethdev_rx_burst_success;
584         eth_dev->tx_pkt_burst = virtual_ethdev_tx_burst_success;
585
586         return eth_dev->data->port_id;
587
588 err:
589         rte_free(pci_dev);
590         rte_free(pci_drv);
591         rte_free(id_table);
592         rte_free(dev_private);
593
594         return -1;
595 }