net/failsafe: add Rx queue start and stop functions
[dpdk.git] / drivers / net / failsafe / failsafe_ops.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright 2017 6WIND S.A.
3  * Copyright 2017 Mellanox Technologies, Ltd
4  */
5
6 #include <stdbool.h>
7 #include <stdint.h>
8 #include <unistd.h>
9
10 #include <rte_debug.h>
11 #include <rte_atomic.h>
12 #include <rte_ethdev_driver.h>
13 #include <rte_malloc.h>
14 #include <rte_flow.h>
15 #include <rte_cycles.h>
16 #include <rte_ethdev.h>
17
18 #include "failsafe_private.h"
19
20 static struct rte_eth_dev_info default_infos = {
21         /* Max possible number of elements */
22         .max_rx_pktlen = UINT32_MAX,
23         .max_rx_queues = RTE_MAX_QUEUES_PER_PORT,
24         .max_tx_queues = RTE_MAX_QUEUES_PER_PORT,
25         .max_mac_addrs = FAILSAFE_MAX_ETHADDR,
26         .max_hash_mac_addrs = UINT32_MAX,
27         .max_vfs = UINT16_MAX,
28         .max_vmdq_pools = UINT16_MAX,
29         .rx_desc_lim = {
30                 .nb_max = UINT16_MAX,
31                 .nb_min = 0,
32                 .nb_align = 1,
33                 .nb_seg_max = UINT16_MAX,
34                 .nb_mtu_seg_max = UINT16_MAX,
35         },
36         .tx_desc_lim = {
37                 .nb_max = UINT16_MAX,
38                 .nb_min = 0,
39                 .nb_align = 1,
40                 .nb_seg_max = UINT16_MAX,
41                 .nb_mtu_seg_max = UINT16_MAX,
42         },
43         /*
44          * Set of capabilities that can be verified upon
45          * configuring a sub-device.
46          */
47         .rx_offload_capa =
48                 DEV_RX_OFFLOAD_VLAN_STRIP |
49                 DEV_RX_OFFLOAD_IPV4_CKSUM |
50                 DEV_RX_OFFLOAD_UDP_CKSUM |
51                 DEV_RX_OFFLOAD_TCP_CKSUM |
52                 DEV_RX_OFFLOAD_TCP_LRO |
53                 DEV_RX_OFFLOAD_QINQ_STRIP |
54                 DEV_RX_OFFLOAD_OUTER_IPV4_CKSUM |
55                 DEV_RX_OFFLOAD_MACSEC_STRIP |
56                 DEV_RX_OFFLOAD_HEADER_SPLIT |
57                 DEV_RX_OFFLOAD_VLAN_FILTER |
58                 DEV_RX_OFFLOAD_VLAN_EXTEND |
59                 DEV_RX_OFFLOAD_JUMBO_FRAME |
60                 DEV_RX_OFFLOAD_SCATTER |
61                 DEV_RX_OFFLOAD_TIMESTAMP |
62                 DEV_RX_OFFLOAD_SECURITY,
63         .rx_queue_offload_capa =
64                 DEV_RX_OFFLOAD_VLAN_STRIP |
65                 DEV_RX_OFFLOAD_IPV4_CKSUM |
66                 DEV_RX_OFFLOAD_UDP_CKSUM |
67                 DEV_RX_OFFLOAD_TCP_CKSUM |
68                 DEV_RX_OFFLOAD_TCP_LRO |
69                 DEV_RX_OFFLOAD_QINQ_STRIP |
70                 DEV_RX_OFFLOAD_OUTER_IPV4_CKSUM |
71                 DEV_RX_OFFLOAD_MACSEC_STRIP |
72                 DEV_RX_OFFLOAD_HEADER_SPLIT |
73                 DEV_RX_OFFLOAD_VLAN_FILTER |
74                 DEV_RX_OFFLOAD_VLAN_EXTEND |
75                 DEV_RX_OFFLOAD_JUMBO_FRAME |
76                 DEV_RX_OFFLOAD_SCATTER |
77                 DEV_RX_OFFLOAD_TIMESTAMP |
78                 DEV_RX_OFFLOAD_SECURITY,
79         .tx_offload_capa =
80                 DEV_TX_OFFLOAD_MULTI_SEGS |
81                 DEV_TX_OFFLOAD_IPV4_CKSUM |
82                 DEV_TX_OFFLOAD_UDP_CKSUM |
83                 DEV_TX_OFFLOAD_TCP_CKSUM |
84                 DEV_TX_OFFLOAD_TCP_TSO,
85         .flow_type_rss_offloads =
86                         ETH_RSS_IP |
87                         ETH_RSS_UDP |
88                         ETH_RSS_TCP,
89 };
90
91 static int
92 fs_dev_configure(struct rte_eth_dev *dev)
93 {
94         struct sub_device *sdev;
95         uint8_t i;
96         int ret;
97
98         fs_lock(dev, 0);
99         FOREACH_SUBDEV(sdev, i, dev) {
100                 int rmv_interrupt = 0;
101                 int lsc_interrupt = 0;
102                 int lsc_enabled;
103
104                 if (sdev->state != DEV_PROBED &&
105                     !(PRIV(dev)->alarm_lock == 0 && sdev->state == DEV_ACTIVE))
106                         continue;
107
108                 rmv_interrupt = ETH(sdev)->data->dev_flags &
109                                 RTE_ETH_DEV_INTR_RMV;
110                 if (rmv_interrupt) {
111                         DEBUG("Enabling RMV interrupts for sub_device %d", i);
112                         dev->data->dev_conf.intr_conf.rmv = 1;
113                 } else {
114                         DEBUG("sub_device %d does not support RMV event", i);
115                 }
116                 lsc_enabled = dev->data->dev_conf.intr_conf.lsc;
117                 lsc_interrupt = lsc_enabled &&
118                                 (ETH(sdev)->data->dev_flags &
119                                  RTE_ETH_DEV_INTR_LSC);
120                 if (lsc_interrupt) {
121                         DEBUG("Enabling LSC interrupts for sub_device %d", i);
122                         dev->data->dev_conf.intr_conf.lsc = 1;
123                 } else if (lsc_enabled && !lsc_interrupt) {
124                         DEBUG("Disabling LSC interrupts for sub_device %d", i);
125                         dev->data->dev_conf.intr_conf.lsc = 0;
126                 }
127                 DEBUG("Configuring sub-device %d", i);
128                 ret = rte_eth_dev_configure(PORT_ID(sdev),
129                                         dev->data->nb_rx_queues,
130                                         dev->data->nb_tx_queues,
131                                         &dev->data->dev_conf);
132                 if (ret) {
133                         if (!fs_err(sdev, ret))
134                                 continue;
135                         ERROR("Could not configure sub_device %d", i);
136                         fs_unlock(dev, 0);
137                         return ret;
138                 }
139                 if (rmv_interrupt && sdev->rmv_callback == 0) {
140                         ret = rte_eth_dev_callback_register(PORT_ID(sdev),
141                                         RTE_ETH_EVENT_INTR_RMV,
142                                         failsafe_eth_rmv_event_callback,
143                                         sdev);
144                         if (ret)
145                                 WARN("Failed to register RMV callback for sub_device %d",
146                                      SUB_ID(sdev));
147                         else
148                                 sdev->rmv_callback = 1;
149                 }
150                 dev->data->dev_conf.intr_conf.rmv = 0;
151                 if (lsc_interrupt && sdev->lsc_callback == 0) {
152                         ret = rte_eth_dev_callback_register(PORT_ID(sdev),
153                                                 RTE_ETH_EVENT_INTR_LSC,
154                                                 failsafe_eth_lsc_event_callback,
155                                                 dev);
156                         if (ret)
157                                 WARN("Failed to register LSC callback for sub_device %d",
158                                      SUB_ID(sdev));
159                         else
160                                 sdev->lsc_callback = 1;
161                 }
162                 dev->data->dev_conf.intr_conf.lsc = lsc_enabled;
163                 sdev->state = DEV_ACTIVE;
164         }
165         if (PRIV(dev)->state < DEV_ACTIVE)
166                 PRIV(dev)->state = DEV_ACTIVE;
167         fs_unlock(dev, 0);
168         return 0;
169 }
170
171 static void
172 fs_set_queues_state_start(struct rte_eth_dev *dev)
173 {
174         struct rxq *rxq;
175         uint16_t i;
176
177         for (i = 0; i < dev->data->nb_rx_queues; i++) {
178                 rxq = dev->data->rx_queues[i];
179                 if (!rxq->info.conf.rx_deferred_start)
180                         dev->data->rx_queue_state[i] =
181                                                 RTE_ETH_QUEUE_STATE_STARTED;
182         }
183 }
184
185 static int
186 fs_dev_start(struct rte_eth_dev *dev)
187 {
188         struct sub_device *sdev;
189         uint8_t i;
190         int ret;
191
192         fs_lock(dev, 0);
193         ret = failsafe_rx_intr_install(dev);
194         if (ret) {
195                 fs_unlock(dev, 0);
196                 return ret;
197         }
198         FOREACH_SUBDEV(sdev, i, dev) {
199                 if (sdev->state != DEV_ACTIVE)
200                         continue;
201                 DEBUG("Starting sub_device %d", i);
202                 ret = rte_eth_dev_start(PORT_ID(sdev));
203                 if (ret) {
204                         if (!fs_err(sdev, ret))
205                                 continue;
206                         fs_unlock(dev, 0);
207                         return ret;
208                 }
209                 ret = failsafe_rx_intr_install_subdevice(sdev);
210                 if (ret) {
211                         if (!fs_err(sdev, ret))
212                                 continue;
213                         rte_eth_dev_stop(PORT_ID(sdev));
214                         fs_unlock(dev, 0);
215                         return ret;
216                 }
217                 sdev->state = DEV_STARTED;
218         }
219         if (PRIV(dev)->state < DEV_STARTED) {
220                 PRIV(dev)->state = DEV_STARTED;
221                 fs_set_queues_state_start(dev);
222         }
223         fs_switch_dev(dev, NULL);
224         fs_unlock(dev, 0);
225         return 0;
226 }
227
228 static void
229 fs_set_queues_state_stop(struct rte_eth_dev *dev)
230 {
231         uint16_t i;
232
233         for (i = 0; i < dev->data->nb_rx_queues; i++)
234                 dev->data->rx_queue_state[i] = RTE_ETH_QUEUE_STATE_STOPPED;
235 }
236
237 static void
238 fs_dev_stop(struct rte_eth_dev *dev)
239 {
240         struct sub_device *sdev;
241         uint8_t i;
242
243         fs_lock(dev, 0);
244         PRIV(dev)->state = DEV_STARTED - 1;
245         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_STARTED) {
246                 rte_eth_dev_stop(PORT_ID(sdev));
247                 failsafe_rx_intr_uninstall_subdevice(sdev);
248                 sdev->state = DEV_STARTED - 1;
249         }
250         failsafe_rx_intr_uninstall(dev);
251         fs_set_queues_state_stop(dev);
252         fs_unlock(dev, 0);
253 }
254
255 static int
256 fs_dev_set_link_up(struct rte_eth_dev *dev)
257 {
258         struct sub_device *sdev;
259         uint8_t i;
260         int ret;
261
262         fs_lock(dev, 0);
263         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
264                 DEBUG("Calling rte_eth_dev_set_link_up on sub_device %d", i);
265                 ret = rte_eth_dev_set_link_up(PORT_ID(sdev));
266                 if ((ret = fs_err(sdev, ret))) {
267                         ERROR("Operation rte_eth_dev_set_link_up failed for sub_device %d"
268                               " with error %d", i, ret);
269                         fs_unlock(dev, 0);
270                         return ret;
271                 }
272         }
273         fs_unlock(dev, 0);
274         return 0;
275 }
276
277 static int
278 fs_dev_set_link_down(struct rte_eth_dev *dev)
279 {
280         struct sub_device *sdev;
281         uint8_t i;
282         int ret;
283
284         fs_lock(dev, 0);
285         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
286                 DEBUG("Calling rte_eth_dev_set_link_down on sub_device %d", i);
287                 ret = rte_eth_dev_set_link_down(PORT_ID(sdev));
288                 if ((ret = fs_err(sdev, ret))) {
289                         ERROR("Operation rte_eth_dev_set_link_down failed for sub_device %d"
290                               " with error %d", i, ret);
291                         fs_unlock(dev, 0);
292                         return ret;
293                 }
294         }
295         fs_unlock(dev, 0);
296         return 0;
297 }
298
299 static void fs_dev_free_queues(struct rte_eth_dev *dev);
300 static void
301 fs_dev_close(struct rte_eth_dev *dev)
302 {
303         struct sub_device *sdev;
304         uint8_t i;
305
306         fs_lock(dev, 0);
307         failsafe_hotplug_alarm_cancel(dev);
308         if (PRIV(dev)->state == DEV_STARTED)
309                 dev->dev_ops->dev_stop(dev);
310         PRIV(dev)->state = DEV_ACTIVE - 1;
311         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
312                 DEBUG("Closing sub_device %d", i);
313                 failsafe_eth_dev_unregister_callbacks(sdev);
314                 rte_eth_dev_close(PORT_ID(sdev));
315                 sdev->state = DEV_ACTIVE - 1;
316         }
317         fs_dev_free_queues(dev);
318         fs_unlock(dev, 0);
319 }
320
321 static int
322 fs_rx_queue_stop(struct rte_eth_dev *dev, uint16_t rx_queue_id)
323 {
324         struct sub_device *sdev;
325         uint8_t i;
326         int ret;
327         int err = 0;
328         bool failure = true;
329
330         fs_lock(dev, 0);
331         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
332                 uint16_t port_id = ETH(sdev)->data->port_id;
333
334                 ret = rte_eth_dev_rx_queue_stop(port_id, rx_queue_id);
335                 ret = fs_err(sdev, ret);
336                 if (ret) {
337                         ERROR("Rx queue stop failed for subdevice %d", i);
338                         err = ret;
339                 } else {
340                         failure = false;
341                 }
342         }
343         dev->data->rx_queue_state[rx_queue_id] = RTE_ETH_QUEUE_STATE_STOPPED;
344         fs_unlock(dev, 0);
345         /* Return 0 in case of at least one successful queue stop */
346         return (failure) ? err : 0;
347 }
348
349 static int
350 fs_rx_queue_start(struct rte_eth_dev *dev, uint16_t rx_queue_id)
351 {
352         struct sub_device *sdev;
353         uint8_t i;
354         int ret;
355
356         fs_lock(dev, 0);
357         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
358                 uint16_t port_id = ETH(sdev)->data->port_id;
359
360                 ret = rte_eth_dev_rx_queue_start(port_id, rx_queue_id);
361                 ret = fs_err(sdev, ret);
362                 if (ret) {
363                         ERROR("Rx queue start failed for subdevice %d", i);
364                         fs_rx_queue_stop(dev, rx_queue_id);
365                         fs_unlock(dev, 0);
366                         return ret;
367                 }
368         }
369         dev->data->rx_queue_state[rx_queue_id] = RTE_ETH_QUEUE_STATE_STARTED;
370         fs_unlock(dev, 0);
371         return 0;
372 }
373
374 static void
375 fs_rx_queue_release(void *queue)
376 {
377         struct rte_eth_dev *dev;
378         struct sub_device *sdev;
379         uint8_t i;
380         struct rxq *rxq;
381
382         if (queue == NULL)
383                 return;
384         rxq = queue;
385         dev = rxq->priv->dev;
386         fs_lock(dev, 0);
387         if (rxq->event_fd > 0)
388                 close(rxq->event_fd);
389         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
390                 if (ETH(sdev)->data->rx_queues != NULL &&
391                     ETH(sdev)->data->rx_queues[rxq->qid] != NULL) {
392                         SUBOPS(sdev, rx_queue_release)
393                                 (ETH(sdev)->data->rx_queues[rxq->qid]);
394                 }
395         }
396         dev->data->rx_queues[rxq->qid] = NULL;
397         rte_free(rxq);
398         fs_unlock(dev, 0);
399 }
400
401 static int
402 fs_rx_queue_setup(struct rte_eth_dev *dev,
403                 uint16_t rx_queue_id,
404                 uint16_t nb_rx_desc,
405                 unsigned int socket_id,
406                 const struct rte_eth_rxconf *rx_conf,
407                 struct rte_mempool *mb_pool)
408 {
409         /*
410          * FIXME: Add a proper interface in rte_eal_interrupts for
411          * allocating eventfd as an interrupt vector.
412          * For the time being, fake as if we are using MSIX interrupts,
413          * this will cause rte_intr_efd_enable to allocate an eventfd for us.
414          */
415         struct rte_intr_handle intr_handle = {
416                 .type = RTE_INTR_HANDLE_VFIO_MSIX,
417                 .efds = { -1, },
418         };
419         struct sub_device *sdev;
420         struct rxq *rxq;
421         uint8_t i;
422         int ret;
423
424         fs_lock(dev, 0);
425         if (rx_conf->rx_deferred_start) {
426                 FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_PROBED) {
427                         if (SUBOPS(sdev, rx_queue_start) == NULL) {
428                                 ERROR("Rx queue deferred start is not "
429                                         "supported for subdevice %d", i);
430                                 fs_unlock(dev, 0);
431                                 return -EINVAL;
432                         }
433                 }
434         }
435         rxq = dev->data->rx_queues[rx_queue_id];
436         if (rxq != NULL) {
437                 fs_rx_queue_release(rxq);
438                 dev->data->rx_queues[rx_queue_id] = NULL;
439         }
440         rxq = rte_zmalloc(NULL,
441                           sizeof(*rxq) +
442                           sizeof(rte_atomic64_t) * PRIV(dev)->subs_tail,
443                           RTE_CACHE_LINE_SIZE);
444         if (rxq == NULL) {
445                 fs_unlock(dev, 0);
446                 return -ENOMEM;
447         }
448         FOREACH_SUBDEV(sdev, i, dev)
449                 rte_atomic64_init(&rxq->refcnt[i]);
450         rxq->qid = rx_queue_id;
451         rxq->socket_id = socket_id;
452         rxq->info.mp = mb_pool;
453         rxq->info.conf = *rx_conf;
454         rxq->info.nb_desc = nb_rx_desc;
455         rxq->priv = PRIV(dev);
456         rxq->sdev = PRIV(dev)->subs;
457         ret = rte_intr_efd_enable(&intr_handle, 1);
458         if (ret < 0) {
459                 fs_unlock(dev, 0);
460                 return ret;
461         }
462         rxq->event_fd = intr_handle.efds[0];
463         dev->data->rx_queues[rx_queue_id] = rxq;
464         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
465                 ret = rte_eth_rx_queue_setup(PORT_ID(sdev),
466                                 rx_queue_id,
467                                 nb_rx_desc, socket_id,
468                                 rx_conf, mb_pool);
469                 if ((ret = fs_err(sdev, ret))) {
470                         ERROR("RX queue setup failed for sub_device %d", i);
471                         goto free_rxq;
472                 }
473         }
474         fs_unlock(dev, 0);
475         return 0;
476 free_rxq:
477         fs_rx_queue_release(rxq);
478         fs_unlock(dev, 0);
479         return ret;
480 }
481
482 static int
483 fs_rx_intr_enable(struct rte_eth_dev *dev, uint16_t idx)
484 {
485         struct rxq *rxq;
486         struct sub_device *sdev;
487         uint8_t i;
488         int ret;
489         int rc = 0;
490
491         fs_lock(dev, 0);
492         if (idx >= dev->data->nb_rx_queues) {
493                 rc = -EINVAL;
494                 goto unlock;
495         }
496         rxq = dev->data->rx_queues[idx];
497         if (rxq == NULL || rxq->event_fd <= 0) {
498                 rc = -EINVAL;
499                 goto unlock;
500         }
501         /* Fail if proxy service is nor running. */
502         if (PRIV(dev)->rxp.sstate != SS_RUNNING) {
503                 ERROR("failsafe interrupt services are not running");
504                 rc = -EAGAIN;
505                 goto unlock;
506         }
507         rxq->enable_events = 1;
508         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
509                 ret = rte_eth_dev_rx_intr_enable(PORT_ID(sdev), idx);
510                 ret = fs_err(sdev, ret);
511                 if (ret)
512                         rc = ret;
513         }
514 unlock:
515         fs_unlock(dev, 0);
516         if (rc)
517                 rte_errno = -rc;
518         return rc;
519 }
520
521 static int
522 fs_rx_intr_disable(struct rte_eth_dev *dev, uint16_t idx)
523 {
524         struct rxq *rxq;
525         struct sub_device *sdev;
526         uint64_t u64;
527         uint8_t i;
528         int rc = 0;
529         int ret;
530
531         fs_lock(dev, 0);
532         if (idx >= dev->data->nb_rx_queues) {
533                 rc = -EINVAL;
534                 goto unlock;
535         }
536         rxq = dev->data->rx_queues[idx];
537         if (rxq == NULL || rxq->event_fd <= 0) {
538                 rc = -EINVAL;
539                 goto unlock;
540         }
541         rxq->enable_events = 0;
542         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
543                 ret = rte_eth_dev_rx_intr_disable(PORT_ID(sdev), idx);
544                 ret = fs_err(sdev, ret);
545                 if (ret)
546                         rc = ret;
547         }
548         /* Clear pending events */
549         while (read(rxq->event_fd, &u64, sizeof(uint64_t)) >  0)
550                 ;
551 unlock:
552         fs_unlock(dev, 0);
553         if (rc)
554                 rte_errno = -rc;
555         return rc;
556 }
557
558 static void
559 fs_tx_queue_release(void *queue)
560 {
561         struct rte_eth_dev *dev;
562         struct sub_device *sdev;
563         uint8_t i;
564         struct txq *txq;
565
566         if (queue == NULL)
567                 return;
568         txq = queue;
569         dev = txq->priv->dev;
570         fs_lock(dev, 0);
571         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
572                 if (ETH(sdev)->data->tx_queues != NULL &&
573                     ETH(sdev)->data->tx_queues[txq->qid] != NULL) {
574                         SUBOPS(sdev, tx_queue_release)
575                                 (ETH(sdev)->data->tx_queues[txq->qid]);
576                 }
577         }
578         dev->data->tx_queues[txq->qid] = NULL;
579         rte_free(txq);
580         fs_unlock(dev, 0);
581 }
582
583 static int
584 fs_tx_queue_setup(struct rte_eth_dev *dev,
585                 uint16_t tx_queue_id,
586                 uint16_t nb_tx_desc,
587                 unsigned int socket_id,
588                 const struct rte_eth_txconf *tx_conf)
589 {
590         struct sub_device *sdev;
591         struct txq *txq;
592         uint8_t i;
593         int ret;
594
595         if (tx_conf->tx_deferred_start) {
596                 ERROR("Tx queue deferred start is not supported");
597                 return -EINVAL;
598         }
599
600         fs_lock(dev, 0);
601         txq = dev->data->tx_queues[tx_queue_id];
602         if (txq != NULL) {
603                 fs_tx_queue_release(txq);
604                 dev->data->tx_queues[tx_queue_id] = NULL;
605         }
606         txq = rte_zmalloc("ethdev TX queue",
607                           sizeof(*txq) +
608                           sizeof(rte_atomic64_t) * PRIV(dev)->subs_tail,
609                           RTE_CACHE_LINE_SIZE);
610         if (txq == NULL) {
611                 fs_unlock(dev, 0);
612                 return -ENOMEM;
613         }
614         FOREACH_SUBDEV(sdev, i, dev)
615                 rte_atomic64_init(&txq->refcnt[i]);
616         txq->qid = tx_queue_id;
617         txq->socket_id = socket_id;
618         txq->info.conf = *tx_conf;
619         txq->info.nb_desc = nb_tx_desc;
620         txq->priv = PRIV(dev);
621         dev->data->tx_queues[tx_queue_id] = txq;
622         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
623                 ret = rte_eth_tx_queue_setup(PORT_ID(sdev),
624                                 tx_queue_id,
625                                 nb_tx_desc, socket_id,
626                                 tx_conf);
627                 if ((ret = fs_err(sdev, ret))) {
628                         ERROR("TX queue setup failed for sub_device %d", i);
629                         goto free_txq;
630                 }
631         }
632         fs_unlock(dev, 0);
633         return 0;
634 free_txq:
635         fs_tx_queue_release(txq);
636         fs_unlock(dev, 0);
637         return ret;
638 }
639
640 static void
641 fs_dev_free_queues(struct rte_eth_dev *dev)
642 {
643         uint16_t i;
644
645         for (i = 0; i < dev->data->nb_rx_queues; i++) {
646                 fs_rx_queue_release(dev->data->rx_queues[i]);
647                 dev->data->rx_queues[i] = NULL;
648         }
649         dev->data->nb_rx_queues = 0;
650         for (i = 0; i < dev->data->nb_tx_queues; i++) {
651                 fs_tx_queue_release(dev->data->tx_queues[i]);
652                 dev->data->tx_queues[i] = NULL;
653         }
654         dev->data->nb_tx_queues = 0;
655 }
656
657 static void
658 fs_promiscuous_enable(struct rte_eth_dev *dev)
659 {
660         struct sub_device *sdev;
661         uint8_t i;
662
663         fs_lock(dev, 0);
664         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE)
665                 rte_eth_promiscuous_enable(PORT_ID(sdev));
666         fs_unlock(dev, 0);
667 }
668
669 static void
670 fs_promiscuous_disable(struct rte_eth_dev *dev)
671 {
672         struct sub_device *sdev;
673         uint8_t i;
674
675         fs_lock(dev, 0);
676         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE)
677                 rte_eth_promiscuous_disable(PORT_ID(sdev));
678         fs_unlock(dev, 0);
679 }
680
681 static void
682 fs_allmulticast_enable(struct rte_eth_dev *dev)
683 {
684         struct sub_device *sdev;
685         uint8_t i;
686
687         fs_lock(dev, 0);
688         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE)
689                 rte_eth_allmulticast_enable(PORT_ID(sdev));
690         fs_unlock(dev, 0);
691 }
692
693 static void
694 fs_allmulticast_disable(struct rte_eth_dev *dev)
695 {
696         struct sub_device *sdev;
697         uint8_t i;
698
699         fs_lock(dev, 0);
700         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE)
701                 rte_eth_allmulticast_disable(PORT_ID(sdev));
702         fs_unlock(dev, 0);
703 }
704
705 static int
706 fs_link_update(struct rte_eth_dev *dev,
707                 int wait_to_complete)
708 {
709         struct sub_device *sdev;
710         uint8_t i;
711         int ret;
712
713         fs_lock(dev, 0);
714         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
715                 DEBUG("Calling link_update on sub_device %d", i);
716                 ret = (SUBOPS(sdev, link_update))(ETH(sdev), wait_to_complete);
717                 if (ret && ret != -1 && sdev->remove == 0 &&
718                     rte_eth_dev_is_removed(PORT_ID(sdev)) == 0) {
719                         ERROR("Link update failed for sub_device %d with error %d",
720                               i, ret);
721                         fs_unlock(dev, 0);
722                         return ret;
723                 }
724         }
725         if (TX_SUBDEV(dev)) {
726                 struct rte_eth_link *l1;
727                 struct rte_eth_link *l2;
728
729                 l1 = &dev->data->dev_link;
730                 l2 = &ETH(TX_SUBDEV(dev))->data->dev_link;
731                 if (memcmp(l1, l2, sizeof(*l1))) {
732                         *l1 = *l2;
733                         fs_unlock(dev, 0);
734                         return 0;
735                 }
736         }
737         fs_unlock(dev, 0);
738         return -1;
739 }
740
741 static int
742 fs_stats_get(struct rte_eth_dev *dev,
743              struct rte_eth_stats *stats)
744 {
745         struct rte_eth_stats backup;
746         struct sub_device *sdev;
747         uint8_t i;
748         int ret;
749
750         fs_lock(dev, 0);
751         rte_memcpy(stats, &PRIV(dev)->stats_accumulator, sizeof(*stats));
752         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
753                 struct rte_eth_stats *snapshot = &sdev->stats_snapshot.stats;
754                 uint64_t *timestamp = &sdev->stats_snapshot.timestamp;
755
756                 rte_memcpy(&backup, snapshot, sizeof(backup));
757                 ret = rte_eth_stats_get(PORT_ID(sdev), snapshot);
758                 if (ret) {
759                         if (!fs_err(sdev, ret)) {
760                                 rte_memcpy(snapshot, &backup, sizeof(backup));
761                                 goto inc;
762                         }
763                         ERROR("Operation rte_eth_stats_get failed for sub_device %d with error %d",
764                                   i, ret);
765                         *timestamp = 0;
766                         fs_unlock(dev, 0);
767                         return ret;
768                 }
769                 *timestamp = rte_rdtsc();
770 inc:
771                 failsafe_stats_increment(stats, snapshot);
772         }
773         fs_unlock(dev, 0);
774         return 0;
775 }
776
777 static void
778 fs_stats_reset(struct rte_eth_dev *dev)
779 {
780         struct sub_device *sdev;
781         uint8_t i;
782
783         fs_lock(dev, 0);
784         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
785                 rte_eth_stats_reset(PORT_ID(sdev));
786                 memset(&sdev->stats_snapshot, 0, sizeof(struct rte_eth_stats));
787         }
788         memset(&PRIV(dev)->stats_accumulator, 0, sizeof(struct rte_eth_stats));
789         fs_unlock(dev, 0);
790 }
791
792 /**
793  * Fail-safe dev_infos_get rules:
794  *
795  * No sub_device:
796  *   Numerables:
797  *      Use the maximum possible values for any field, so as not
798  *      to impede any further configuration effort.
799  *   Capabilities:
800  *      Limits capabilities to those that are understood by the
801  *      fail-safe PMD. This understanding stems from the fail-safe
802  *      being capable of verifying that the related capability is
803  *      expressed within the device configuration (struct rte_eth_conf).
804  *
805  * At least one probed sub_device:
806  *   Numerables:
807  *      Uses values from the active probed sub_device
808  *      The rationale here is that if any sub_device is less capable
809  *      (for example concerning the number of queues) than the active
810  *      sub_device, then its subsequent configuration will fail.
811  *      It is impossible to foresee this failure when the failing sub_device
812  *      is supposed to be plugged-in later on, so the configuration process
813  *      is the single point of failure and error reporting.
814  *   Capabilities:
815  *      Uses a logical AND of RX capabilities among
816  *      all sub_devices and the default capabilities.
817  *      Uses a logical AND of TX capabilities among
818  *      the active probed sub_device and the default capabilities.
819  *
820  */
821 static void
822 fs_dev_infos_get(struct rte_eth_dev *dev,
823                   struct rte_eth_dev_info *infos)
824 {
825         struct sub_device *sdev;
826         uint8_t i;
827
828         sdev = TX_SUBDEV(dev);
829         if (sdev == NULL) {
830                 DEBUG("No probed device, using default infos");
831                 rte_memcpy(&PRIV(dev)->infos, &default_infos,
832                            sizeof(default_infos));
833         } else {
834                 uint64_t rx_offload_capa;
835                 uint64_t rxq_offload_capa;
836                 uint64_t rss_hf_offload_capa;
837
838                 rx_offload_capa = default_infos.rx_offload_capa;
839                 rxq_offload_capa = default_infos.rx_queue_offload_capa;
840                 rss_hf_offload_capa = default_infos.flow_type_rss_offloads;
841                 FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_PROBED) {
842                         rte_eth_dev_info_get(PORT_ID(sdev),
843                                         &PRIV(dev)->infos);
844                         rx_offload_capa &= PRIV(dev)->infos.rx_offload_capa;
845                         rxq_offload_capa &=
846                                         PRIV(dev)->infos.rx_queue_offload_capa;
847                         rss_hf_offload_capa &=
848                                         PRIV(dev)->infos.flow_type_rss_offloads;
849                 }
850                 sdev = TX_SUBDEV(dev);
851                 rte_eth_dev_info_get(PORT_ID(sdev), &PRIV(dev)->infos);
852                 PRIV(dev)->infos.rx_offload_capa = rx_offload_capa;
853                 PRIV(dev)->infos.rx_queue_offload_capa = rxq_offload_capa;
854                 PRIV(dev)->infos.flow_type_rss_offloads = rss_hf_offload_capa;
855                 PRIV(dev)->infos.tx_offload_capa &=
856                                         default_infos.tx_offload_capa;
857                 PRIV(dev)->infos.tx_queue_offload_capa &=
858                                         default_infos.tx_queue_offload_capa;
859         }
860         rte_memcpy(infos, &PRIV(dev)->infos, sizeof(*infos));
861 }
862
863 static const uint32_t *
864 fs_dev_supported_ptypes_get(struct rte_eth_dev *dev)
865 {
866         struct sub_device *sdev;
867         struct rte_eth_dev *edev;
868         const uint32_t *ret;
869
870         fs_lock(dev, 0);
871         sdev = TX_SUBDEV(dev);
872         if (sdev == NULL) {
873                 ret = NULL;
874                 goto unlock;
875         }
876         edev = ETH(sdev);
877         /* ENOTSUP: counts as no supported ptypes */
878         if (SUBOPS(sdev, dev_supported_ptypes_get) == NULL) {
879                 ret = NULL;
880                 goto unlock;
881         }
882         /*
883          * The API does not permit to do a clean AND of all ptypes,
884          * It is also incomplete by design and we do not really care
885          * to have a best possible value in this context.
886          * We just return the ptypes of the device of highest
887          * priority, usually the PREFERRED device.
888          */
889         ret = SUBOPS(sdev, dev_supported_ptypes_get)(edev);
890 unlock:
891         fs_unlock(dev, 0);
892         return ret;
893 }
894
895 static int
896 fs_mtu_set(struct rte_eth_dev *dev, uint16_t mtu)
897 {
898         struct sub_device *sdev;
899         uint8_t i;
900         int ret;
901
902         fs_lock(dev, 0);
903         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
904                 DEBUG("Calling rte_eth_dev_set_mtu on sub_device %d", i);
905                 ret = rte_eth_dev_set_mtu(PORT_ID(sdev), mtu);
906                 if ((ret = fs_err(sdev, ret))) {
907                         ERROR("Operation rte_eth_dev_set_mtu failed for sub_device %d with error %d",
908                               i, ret);
909                         fs_unlock(dev, 0);
910                         return ret;
911                 }
912         }
913         fs_unlock(dev, 0);
914         return 0;
915 }
916
917 static int
918 fs_vlan_filter_set(struct rte_eth_dev *dev, uint16_t vlan_id, int on)
919 {
920         struct sub_device *sdev;
921         uint8_t i;
922         int ret;
923
924         fs_lock(dev, 0);
925         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
926                 DEBUG("Calling rte_eth_dev_vlan_filter on sub_device %d", i);
927                 ret = rte_eth_dev_vlan_filter(PORT_ID(sdev), vlan_id, on);
928                 if ((ret = fs_err(sdev, ret))) {
929                         ERROR("Operation rte_eth_dev_vlan_filter failed for sub_device %d"
930                               " with error %d", i, ret);
931                         fs_unlock(dev, 0);
932                         return ret;
933                 }
934         }
935         fs_unlock(dev, 0);
936         return 0;
937 }
938
939 static int
940 fs_flow_ctrl_get(struct rte_eth_dev *dev,
941                 struct rte_eth_fc_conf *fc_conf)
942 {
943         struct sub_device *sdev;
944         int ret;
945
946         fs_lock(dev, 0);
947         sdev = TX_SUBDEV(dev);
948         if (sdev == NULL) {
949                 ret = 0;
950                 goto unlock;
951         }
952         if (SUBOPS(sdev, flow_ctrl_get) == NULL) {
953                 ret = -ENOTSUP;
954                 goto unlock;
955         }
956         ret = SUBOPS(sdev, flow_ctrl_get)(ETH(sdev), fc_conf);
957 unlock:
958         fs_unlock(dev, 0);
959         return ret;
960 }
961
962 static int
963 fs_flow_ctrl_set(struct rte_eth_dev *dev,
964                 struct rte_eth_fc_conf *fc_conf)
965 {
966         struct sub_device *sdev;
967         uint8_t i;
968         int ret;
969
970         fs_lock(dev, 0);
971         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
972                 DEBUG("Calling rte_eth_dev_flow_ctrl_set on sub_device %d", i);
973                 ret = rte_eth_dev_flow_ctrl_set(PORT_ID(sdev), fc_conf);
974                 if ((ret = fs_err(sdev, ret))) {
975                         ERROR("Operation rte_eth_dev_flow_ctrl_set failed for sub_device %d"
976                               " with error %d", i, ret);
977                         fs_unlock(dev, 0);
978                         return ret;
979                 }
980         }
981         fs_unlock(dev, 0);
982         return 0;
983 }
984
985 static void
986 fs_mac_addr_remove(struct rte_eth_dev *dev, uint32_t index)
987 {
988         struct sub_device *sdev;
989         uint8_t i;
990
991         fs_lock(dev, 0);
992         /* No check: already done within the rte_eth_dev_mac_addr_remove
993          * call for the fail-safe device.
994          */
995         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE)
996                 rte_eth_dev_mac_addr_remove(PORT_ID(sdev),
997                                 &dev->data->mac_addrs[index]);
998         PRIV(dev)->mac_addr_pool[index] = 0;
999         fs_unlock(dev, 0);
1000 }
1001
1002 static int
1003 fs_mac_addr_add(struct rte_eth_dev *dev,
1004                 struct ether_addr *mac_addr,
1005                 uint32_t index,
1006                 uint32_t vmdq)
1007 {
1008         struct sub_device *sdev;
1009         int ret;
1010         uint8_t i;
1011
1012         RTE_ASSERT(index < FAILSAFE_MAX_ETHADDR);
1013         fs_lock(dev, 0);
1014         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
1015                 ret = rte_eth_dev_mac_addr_add(PORT_ID(sdev), mac_addr, vmdq);
1016                 if ((ret = fs_err(sdev, ret))) {
1017                         ERROR("Operation rte_eth_dev_mac_addr_add failed for sub_device %"
1018                               PRIu8 " with error %d", i, ret);
1019                         fs_unlock(dev, 0);
1020                         return ret;
1021                 }
1022         }
1023         if (index >= PRIV(dev)->nb_mac_addr) {
1024                 DEBUG("Growing mac_addrs array");
1025                 PRIV(dev)->nb_mac_addr = index;
1026         }
1027         PRIV(dev)->mac_addr_pool[index] = vmdq;
1028         fs_unlock(dev, 0);
1029         return 0;
1030 }
1031
1032 static int
1033 fs_mac_addr_set(struct rte_eth_dev *dev, struct ether_addr *mac_addr)
1034 {
1035         struct sub_device *sdev;
1036         uint8_t i;
1037         int ret;
1038
1039         fs_lock(dev, 0);
1040         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
1041                 ret = rte_eth_dev_default_mac_addr_set(PORT_ID(sdev), mac_addr);
1042                 ret = fs_err(sdev, ret);
1043                 if (ret) {
1044                         ERROR("Operation rte_eth_dev_mac_addr_set failed for sub_device %d with error %d",
1045                                 i, ret);
1046                         fs_unlock(dev, 0);
1047                         return ret;
1048                 }
1049         }
1050         fs_unlock(dev, 0);
1051
1052         return 0;
1053 }
1054
1055 static int
1056 fs_rss_hash_update(struct rte_eth_dev *dev,
1057                         struct rte_eth_rss_conf *rss_conf)
1058 {
1059         struct sub_device *sdev;
1060         uint8_t i;
1061         int ret;
1062
1063         fs_lock(dev, 0);
1064         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
1065                 ret = rte_eth_dev_rss_hash_update(PORT_ID(sdev), rss_conf);
1066                 ret = fs_err(sdev, ret);
1067                 if (ret) {
1068                         ERROR("Operation rte_eth_dev_rss_hash_update"
1069                                 " failed for sub_device %d with error %d",
1070                                 i, ret);
1071                         fs_unlock(dev, 0);
1072                         return ret;
1073                 }
1074         }
1075         fs_unlock(dev, 0);
1076
1077         return 0;
1078 }
1079
1080 static int
1081 fs_filter_ctrl(struct rte_eth_dev *dev,
1082                 enum rte_filter_type type,
1083                 enum rte_filter_op op,
1084                 void *arg)
1085 {
1086         struct sub_device *sdev;
1087         uint8_t i;
1088         int ret;
1089
1090         if (type == RTE_ETH_FILTER_GENERIC &&
1091             op == RTE_ETH_FILTER_GET) {
1092                 *(const void **)arg = &fs_flow_ops;
1093                 return 0;
1094         }
1095         fs_lock(dev, 0);
1096         FOREACH_SUBDEV_STATE(sdev, i, dev, DEV_ACTIVE) {
1097                 DEBUG("Calling rte_eth_dev_filter_ctrl on sub_device %d", i);
1098                 ret = rte_eth_dev_filter_ctrl(PORT_ID(sdev), type, op, arg);
1099                 if ((ret = fs_err(sdev, ret))) {
1100                         ERROR("Operation rte_eth_dev_filter_ctrl failed for sub_device %d"
1101                               " with error %d", i, ret);
1102                         fs_unlock(dev, 0);
1103                         return ret;
1104                 }
1105         }
1106         fs_unlock(dev, 0);
1107         return 0;
1108 }
1109
1110 const struct eth_dev_ops failsafe_ops = {
1111         .dev_configure = fs_dev_configure,
1112         .dev_start = fs_dev_start,
1113         .dev_stop = fs_dev_stop,
1114         .dev_set_link_down = fs_dev_set_link_down,
1115         .dev_set_link_up = fs_dev_set_link_up,
1116         .dev_close = fs_dev_close,
1117         .promiscuous_enable = fs_promiscuous_enable,
1118         .promiscuous_disable = fs_promiscuous_disable,
1119         .allmulticast_enable = fs_allmulticast_enable,
1120         .allmulticast_disable = fs_allmulticast_disable,
1121         .link_update = fs_link_update,
1122         .stats_get = fs_stats_get,
1123         .stats_reset = fs_stats_reset,
1124         .dev_infos_get = fs_dev_infos_get,
1125         .dev_supported_ptypes_get = fs_dev_supported_ptypes_get,
1126         .mtu_set = fs_mtu_set,
1127         .vlan_filter_set = fs_vlan_filter_set,
1128         .rx_queue_start = fs_rx_queue_start,
1129         .rx_queue_stop = fs_rx_queue_stop,
1130         .rx_queue_setup = fs_rx_queue_setup,
1131         .tx_queue_setup = fs_tx_queue_setup,
1132         .rx_queue_release = fs_rx_queue_release,
1133         .tx_queue_release = fs_tx_queue_release,
1134         .rx_queue_intr_enable = fs_rx_intr_enable,
1135         .rx_queue_intr_disable = fs_rx_intr_disable,
1136         .flow_ctrl_get = fs_flow_ctrl_get,
1137         .flow_ctrl_set = fs_flow_ctrl_set,
1138         .mac_addr_remove = fs_mac_addr_remove,
1139         .mac_addr_add = fs_mac_addr_add,
1140         .mac_addr_set = fs_mac_addr_set,
1141         .rss_hash_update = fs_rss_hash_update,
1142         .filter_ctrl = fs_filter_ctrl,
1143 };