bus/dpaa: add accessor for netcfg
[dpdk.git] / drivers / bus / dpaa / dpaa_bus.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  *
3  *   Copyright 2017-2019 NXP
4  *
5  */
6 /* System headers */
7 #include <stdio.h>
8 #include <inttypes.h>
9 #include <unistd.h>
10 #include <limits.h>
11 #include <sched.h>
12 #include <signal.h>
13 #include <pthread.h>
14 #include <sys/types.h>
15 #include <sys/syscall.h>
16
17 #include <rte_byteorder.h>
18 #include <rte_common.h>
19 #include <rte_interrupts.h>
20 #include <rte_log.h>
21 #include <rte_debug.h>
22 #include <rte_atomic.h>
23 #include <rte_branch_prediction.h>
24 #include <rte_memory.h>
25 #include <rte_tailq.h>
26 #include <rte_eal.h>
27 #include <rte_alarm.h>
28 #include <rte_ether.h>
29 #include <rte_ethdev_driver.h>
30 #include <rte_malloc.h>
31 #include <rte_ring.h>
32 #include <rte_bus.h>
33 #include <rte_mbuf_pool_ops.h>
34
35 #include <dpaa_of.h>
36 #include <rte_dpaa_bus.h>
37 #include <rte_dpaa_logs.h>
38 #include <dpaax_iova_table.h>
39
40 #include <fsl_usd.h>
41 #include <fsl_qman.h>
42 #include <fsl_bman.h>
43 #include <netcfg.h>
44
45 int dpaa_logtype_bus;
46
47 static struct rte_dpaa_bus rte_dpaa_bus;
48 struct netcfg_info *dpaa_netcfg;
49
50 /* define a variable to hold the portal_key, once created.*/
51 static pthread_key_t dpaa_portal_key;
52
53 unsigned int dpaa_svr_family;
54
55 #define FSL_DPAA_BUS_NAME       dpaa_bus
56
57 RTE_DEFINE_PER_LCORE(bool, dpaa_io);
58 RTE_DEFINE_PER_LCORE(struct dpaa_portal_dqrr, held_bufs);
59
60 struct fm_eth_port_cfg *
61 dpaa_get_eth_port_cfg(int dev_id)
62 {
63         return &dpaa_netcfg->port_cfg[dev_id];
64 }
65
66 static int
67 compare_dpaa_devices(struct rte_dpaa_device *dev1,
68                      struct rte_dpaa_device *dev2)
69 {
70         int comp = 0;
71
72         /* Segragating ETH from SEC devices */
73         if (dev1->device_type > dev2->device_type)
74                 comp = 1;
75         else if (dev1->device_type < dev2->device_type)
76                 comp = -1;
77         else
78                 comp = 0;
79
80         if ((comp != 0) || (dev1->device_type != FSL_DPAA_ETH))
81                 return comp;
82
83         if (dev1->id.fman_id > dev2->id.fman_id) {
84                 comp = 1;
85         } else if (dev1->id.fman_id < dev2->id.fman_id) {
86                 comp = -1;
87         } else {
88                 /* FMAN ids match, check for mac_id */
89                 if (dev1->id.mac_id > dev2->id.mac_id)
90                         comp = 1;
91                 else if (dev1->id.mac_id < dev2->id.mac_id)
92                         comp = -1;
93                 else
94                         comp = 0;
95         }
96
97         return comp;
98 }
99
100 static inline void
101 dpaa_add_to_device_list(struct rte_dpaa_device *newdev)
102 {
103         int comp, inserted = 0;
104         struct rte_dpaa_device *dev = NULL;
105         struct rte_dpaa_device *tdev = NULL;
106
107         TAILQ_FOREACH_SAFE(dev, &rte_dpaa_bus.device_list, next, tdev) {
108                 comp = compare_dpaa_devices(newdev, dev);
109                 if (comp < 0) {
110                         TAILQ_INSERT_BEFORE(dev, newdev, next);
111                         inserted = 1;
112                         break;
113                 }
114         }
115
116         if (!inserted)
117                 TAILQ_INSERT_TAIL(&rte_dpaa_bus.device_list, newdev, next);
118 }
119
120 /*
121  * Reads the SEC device from DTS
122  * Returns -1 if SEC devices not available, 0 otherwise
123  */
124 static inline int
125 dpaa_sec_available(void)
126 {
127         const struct device_node *caam_node;
128
129         for_each_compatible_node(caam_node, NULL, "fsl,sec-v4.0") {
130                 return 0;
131         }
132
133         return -1;
134 }
135
136 static void dpaa_clean_device_list(void);
137
138 static struct rte_devargs *
139 dpaa_devargs_lookup(struct rte_dpaa_device *dev)
140 {
141         struct rte_devargs *devargs;
142         char dev_name[32];
143
144         RTE_EAL_DEVARGS_FOREACH("dpaa_bus", devargs) {
145                 devargs->bus->parse(devargs->name, &dev_name);
146                 if (strcmp(dev_name, dev->device.name) == 0) {
147                         DPAA_BUS_INFO("**Devargs matched %s", dev_name);
148                         return devargs;
149                 }
150         }
151         return NULL;
152 }
153
154 static int
155 dpaa_create_device_list(void)
156 {
157         int i;
158         int ret;
159         struct rte_dpaa_device *dev;
160         struct fm_eth_port_cfg *cfg;
161         struct fman_if *fman_intf;
162
163         /* Creating Ethernet Devices */
164         for (i = 0; i < dpaa_netcfg->num_ethports; i++) {
165                 dev = calloc(1, sizeof(struct rte_dpaa_device));
166                 if (!dev) {
167                         DPAA_BUS_LOG(ERR, "Failed to allocate ETH devices");
168                         ret = -ENOMEM;
169                         goto cleanup;
170                 }
171
172                 dev->device.bus = &rte_dpaa_bus.bus;
173
174                 cfg = &dpaa_netcfg->port_cfg[i];
175                 fman_intf = cfg->fman_if;
176
177                 /* Device identifiers */
178                 dev->id.fman_id = fman_intf->fman_idx + 1;
179                 dev->id.mac_id = fman_intf->mac_idx;
180                 dev->device_type = FSL_DPAA_ETH;
181                 dev->id.dev_id = i;
182
183                 /* Create device name */
184                 memset(dev->name, 0, RTE_ETH_NAME_MAX_LEN);
185                 sprintf(dev->name, "fm%d-mac%d", (fman_intf->fman_idx + 1),
186                         fman_intf->mac_idx);
187                 DPAA_BUS_LOG(INFO, "%s netdev added", dev->name);
188                 dev->device.name = dev->name;
189                 dev->device.devargs = dpaa_devargs_lookup(dev);
190
191                 dpaa_add_to_device_list(dev);
192         }
193
194         rte_dpaa_bus.device_count = i;
195
196         /* Unlike case of ETH, RTE_LIBRTE_DPAA_MAX_CRYPTODEV SEC devices are
197          * constantly created only if "sec" property is found in the device
198          * tree. Logically there is no limit for number of devices (QI
199          * interfaces) that can be created.
200          */
201
202         if (dpaa_sec_available()) {
203                 DPAA_BUS_LOG(INFO, "DPAA SEC devices are not available");
204                 return 0;
205         }
206
207         /* Creating SEC Devices */
208         for (i = 0; i < RTE_LIBRTE_DPAA_MAX_CRYPTODEV; i++) {
209                 dev = calloc(1, sizeof(struct rte_dpaa_device));
210                 if (!dev) {
211                         DPAA_BUS_LOG(ERR, "Failed to allocate SEC devices");
212                         ret = -1;
213                         goto cleanup;
214                 }
215
216                 dev->device_type = FSL_DPAA_CRYPTO;
217                 dev->id.dev_id = rte_dpaa_bus.device_count + i;
218
219                 /* Even though RTE_CRYPTODEV_NAME_MAX_LEN is valid length of
220                  * crypto PMD, using RTE_ETH_NAME_MAX_LEN as that is the size
221                  * allocated for dev->name/
222                  */
223                 memset(dev->name, 0, RTE_ETH_NAME_MAX_LEN);
224                 sprintf(dev->name, "dpaa_sec-%d", i+1);
225                 DPAA_BUS_LOG(INFO, "%s cryptodev added", dev->name);
226                 dev->device.name = dev->name;
227                 dev->device.devargs = dpaa_devargs_lookup(dev);
228
229                 dpaa_add_to_device_list(dev);
230         }
231
232         rte_dpaa_bus.device_count += i;
233
234         return 0;
235
236 cleanup:
237         dpaa_clean_device_list();
238         return ret;
239 }
240
241 static void
242 dpaa_clean_device_list(void)
243 {
244         struct rte_dpaa_device *dev = NULL;
245         struct rte_dpaa_device *tdev = NULL;
246
247         TAILQ_FOREACH_SAFE(dev, &rte_dpaa_bus.device_list, next, tdev) {
248                 TAILQ_REMOVE(&rte_dpaa_bus.device_list, dev, next);
249                 free(dev);
250                 dev = NULL;
251         }
252 }
253
254 int rte_dpaa_portal_init(void *arg)
255 {
256         unsigned int cpu, lcore = rte_lcore_id();
257         int ret;
258         struct dpaa_portal *dpaa_io_portal;
259
260         BUS_INIT_FUNC_TRACE();
261
262         if ((size_t)arg == 1 || lcore == LCORE_ID_ANY)
263                 lcore = rte_get_master_lcore();
264         else
265                 if (lcore >= RTE_MAX_LCORE)
266                         return -1;
267
268         cpu = rte_lcore_to_cpu_id(lcore);
269
270         /* Initialise bman thread portals */
271         ret = bman_thread_init();
272         if (ret) {
273                 DPAA_BUS_LOG(ERR, "bman_thread_init failed on core %u"
274                              " (lcore=%u) with ret: %d", cpu, lcore, ret);
275                 return ret;
276         }
277
278         DPAA_BUS_LOG(DEBUG, "BMAN thread initialized - CPU=%d lcore=%d",
279                      cpu, lcore);
280
281         /* Initialise qman thread portals */
282         ret = qman_thread_init();
283         if (ret) {
284                 DPAA_BUS_LOG(ERR, "qman_thread_init failed on core %u"
285                             " (lcore=%u) with ret: %d", cpu, lcore, ret);
286                 bman_thread_finish();
287                 return ret;
288         }
289
290         DPAA_BUS_LOG(DEBUG, "QMAN thread initialized - CPU=%d lcore=%d",
291                      cpu, lcore);
292
293         dpaa_io_portal = rte_malloc(NULL, sizeof(struct dpaa_portal),
294                                     RTE_CACHE_LINE_SIZE);
295         if (!dpaa_io_portal) {
296                 DPAA_BUS_LOG(ERR, "Unable to allocate memory");
297                 bman_thread_finish();
298                 qman_thread_finish();
299                 return -ENOMEM;
300         }
301
302         dpaa_io_portal->qman_idx = qman_get_portal_index();
303         dpaa_io_portal->bman_idx = bman_get_portal_index();
304         dpaa_io_portal->tid = syscall(SYS_gettid);
305
306         ret = pthread_setspecific(dpaa_portal_key, (void *)dpaa_io_portal);
307         if (ret) {
308                 DPAA_BUS_LOG(ERR, "pthread_setspecific failed on core %u"
309                              " (lcore=%u) with ret: %d", cpu, lcore, ret);
310                 dpaa_portal_finish(NULL);
311
312                 return ret;
313         }
314
315         RTE_PER_LCORE(dpaa_io) = true;
316
317         DPAA_BUS_LOG(DEBUG, "QMAN thread initialized");
318
319         return 0;
320 }
321
322 int
323 rte_dpaa_portal_fq_init(void *arg, struct qman_fq *fq)
324 {
325         /* Affine above created portal with channel*/
326         u32 sdqcr;
327         int ret;
328
329         if (unlikely(!RTE_PER_LCORE(dpaa_io))) {
330                 ret = rte_dpaa_portal_init(arg);
331                 if (ret < 0) {
332                         DPAA_BUS_LOG(ERR, "portal initialization failure");
333                         return ret;
334                 }
335         }
336
337         /* Initialise qman specific portals */
338         ret = fsl_qman_fq_portal_init(fq->qp);
339         if (ret) {
340                 DPAA_BUS_LOG(ERR, "Unable to init fq portal");
341                 return -1;
342         }
343
344         sdqcr = QM_SDQCR_CHANNELS_POOL_CONV(fq->ch_id);
345         qman_static_dequeue_add(sdqcr, fq->qp);
346
347         return 0;
348 }
349
350 int rte_dpaa_portal_fq_close(struct qman_fq *fq)
351 {
352         return fsl_qman_fq_portal_destroy(fq->qp);
353 }
354
355 void
356 dpaa_portal_finish(void *arg)
357 {
358         struct dpaa_portal *dpaa_io_portal = (struct dpaa_portal *)arg;
359
360         if (!dpaa_io_portal) {
361                 DPAA_BUS_LOG(DEBUG, "Portal already cleaned");
362                 return;
363         }
364
365         bman_thread_finish();
366         qman_thread_finish();
367
368         pthread_setspecific(dpaa_portal_key, NULL);
369
370         rte_free(dpaa_io_portal);
371         dpaa_io_portal = NULL;
372
373         RTE_PER_LCORE(dpaa_io) = false;
374 }
375
376 static int
377 rte_dpaa_bus_parse(const char *name, void *out_name)
378 {
379         int i, j;
380         int max_fman = 2, max_macs = 16;
381         char *dup_name;
382         char *sep = NULL;
383
384         /* There are two ways of passing device name, with and without
385          * separator. "dpaa_bus:fm1-mac3" with separator, and "fm1-mac3"
386          * without separator. Both need to be handled.
387          * It is also possible that "name=fm1-mac3" is passed along.
388          */
389         DPAA_BUS_DEBUG("Parse device name (%s)", name);
390
391         /* Check for dpaa_bus:fm1-mac3 style */
392         dup_name = strdup(name);
393         sep = strchr(dup_name, ':');
394         if (!sep)
395                 /* If not, check for name=fm1-mac3 style */
396                 sep = strchr(dup_name, '=');
397
398         if (sep)
399                 /* jump over the seprator */
400                 sep = (char *) (sep + 1);
401         else
402                 sep = dup_name;
403
404         for (i = 0; i < max_fman; i++) {
405                 for (j = 0; j < max_macs; j++) {
406                         char fm_name[16];
407                         snprintf(fm_name, 16, "fm%d-mac%d", i, j);
408                         if (strcmp(fm_name, sep) == 0) {
409                                 if (out_name)
410                                         strcpy(out_name, sep);
411                                 free(dup_name);
412                                 return 0;
413                         }
414                 }
415         }
416
417         for (i = 0; i < RTE_LIBRTE_DPAA_MAX_CRYPTODEV; i++) {
418                 char sec_name[16];
419
420                 snprintf(sec_name, 16, "dpaa_sec-%d", i+1);
421                 if (strcmp(sec_name, sep) == 0) {
422                         if (out_name)
423                                 strcpy(out_name, sep);
424                         free(dup_name);
425                         return 0;
426                 }
427         }
428
429         free(dup_name);
430         return -EINVAL;
431 }
432
433 #define DPAA_DEV_PATH1 "/sys/devices/platform/soc/soc:fsl,dpaa"
434 #define DPAA_DEV_PATH2 "/sys/devices/platform/fsl,dpaa"
435
436 static int
437 rte_dpaa_bus_scan(void)
438 {
439         int ret;
440
441         BUS_INIT_FUNC_TRACE();
442
443         if ((access(DPAA_DEV_PATH1, F_OK) != 0) &&
444             (access(DPAA_DEV_PATH2, F_OK) != 0)) {
445                 RTE_LOG(DEBUG, EAL, "DPAA Bus not present. Skipping.\n");
446                 return 0;
447         }
448
449         if (rte_dpaa_bus.detected)
450                 return 0;
451
452         rte_dpaa_bus.detected = 1;
453
454         /* create the key, supplying a function that'll be invoked
455          * when a portal affined thread will be deleted.
456          */
457         ret = pthread_key_create(&dpaa_portal_key, dpaa_portal_finish);
458         if (ret) {
459                 DPAA_BUS_LOG(DEBUG, "Unable to create pthread key. (%d)", ret);
460                 dpaa_clean_device_list();
461                 return ret;
462         }
463
464         return 0;
465 }
466
467 /* register a dpaa bus based dpaa driver */
468 void
469 rte_dpaa_driver_register(struct rte_dpaa_driver *driver)
470 {
471         RTE_VERIFY(driver);
472
473         BUS_INIT_FUNC_TRACE();
474
475         TAILQ_INSERT_TAIL(&rte_dpaa_bus.driver_list, driver, next);
476         /* Update Bus references */
477         driver->dpaa_bus = &rte_dpaa_bus;
478 }
479
480 /* un-register a dpaa bus based dpaa driver */
481 void
482 rte_dpaa_driver_unregister(struct rte_dpaa_driver *driver)
483 {
484         struct rte_dpaa_bus *dpaa_bus;
485
486         BUS_INIT_FUNC_TRACE();
487
488         dpaa_bus = driver->dpaa_bus;
489
490         TAILQ_REMOVE(&dpaa_bus->driver_list, driver, next);
491         /* Update Bus references */
492         driver->dpaa_bus = NULL;
493 }
494
495 static int
496 rte_dpaa_device_match(struct rte_dpaa_driver *drv,
497                       struct rte_dpaa_device *dev)
498 {
499         if (!drv || !dev) {
500                 DPAA_BUS_DEBUG("Invalid drv or dev received.");
501                 return -1;
502         }
503
504         if (drv->drv_type == dev->device_type)
505                 return 0;
506
507         return -1;
508 }
509
510 static int
511 rte_dpaa_bus_dev_build(void)
512 {
513         int ret;
514
515         /* Load the device-tree driver */
516         ret = of_init();
517         if (ret) {
518                 DPAA_BUS_LOG(ERR, "of_init failed with ret: %d", ret);
519                 return -1;
520         }
521
522         /* Get the interface configurations from device-tree */
523         dpaa_netcfg = netcfg_acquire();
524         if (!dpaa_netcfg) {
525                 DPAA_BUS_LOG(ERR, "netcfg_acquire failed");
526                 return -EINVAL;
527         }
528
529         RTE_LOG(NOTICE, EAL, "DPAA Bus Detected\n");
530
531         if (!dpaa_netcfg->num_ethports) {
532                 DPAA_BUS_LOG(INFO, "no network interfaces available");
533                 /* This is not an error */
534                 return 0;
535         }
536
537 #ifdef RTE_LIBRTE_DPAA_DEBUG_DRIVER
538         dump_netcfg(dpaa_netcfg);
539 #endif
540
541         DPAA_BUS_LOG(DEBUG, "Number of ethernet devices = %d",
542                      dpaa_netcfg->num_ethports);
543         ret = dpaa_create_device_list();
544         if (ret) {
545                 DPAA_BUS_LOG(ERR, "Unable to create device list. (%d)", ret);
546                 return ret;
547         }
548         return 0;
549 }
550
551 static int
552 rte_dpaa_bus_probe(void)
553 {
554         int ret = -1;
555         struct rte_dpaa_device *dev;
556         struct rte_dpaa_driver *drv;
557         FILE *svr_file = NULL;
558         unsigned int svr_ver;
559         int probe_all = rte_dpaa_bus.bus.conf.scan_mode != RTE_BUS_SCAN_WHITELIST;
560         static int process_once;
561
562         /* If DPAA bus is not present nothing needs to be done */
563         if (!rte_dpaa_bus.detected)
564                 return 0;
565
566         /* Device list creation is only done once */
567         if (!process_once) {
568                 rte_dpaa_bus_dev_build();
569                 if (rte_eal_process_type() == RTE_PROC_PRIMARY) {
570                         /* One time load of Qman/Bman drivers */
571                         ret = qman_global_init();
572                         if (ret) {
573                                 DPAA_BUS_ERR("QMAN initialization failed: %d",
574                                              ret);
575                                 return ret;
576                         }
577                         ret = bman_global_init();
578                         if (ret) {
579                                 DPAA_BUS_ERR("BMAN initialization failed: %d",
580                                              ret);
581                                 return ret;
582                         }
583                 }
584         }
585         process_once = 1;
586
587         /* If no device present on DPAA bus nothing needs to be done */
588         if (TAILQ_EMPTY(&rte_dpaa_bus.device_list))
589                 return 0;
590
591         svr_file = fopen(DPAA_SOC_ID_FILE, "r");
592         if (svr_file) {
593                 if (fscanf(svr_file, "svr:%x", &svr_ver) > 0)
594                         dpaa_svr_family = svr_ver & SVR_MASK;
595                 fclose(svr_file);
596         }
597
598         /* And initialize the PA->VA translation table */
599         dpaax_iova_table_populate();
600
601         /* For each registered driver, and device, call the driver->probe */
602         TAILQ_FOREACH(dev, &rte_dpaa_bus.device_list, next) {
603                 TAILQ_FOREACH(drv, &rte_dpaa_bus.driver_list, next) {
604                         ret = rte_dpaa_device_match(drv, dev);
605                         if (ret)
606                                 continue;
607
608                         if (rte_dev_is_probed(&dev->device))
609                                 continue;
610
611                         if (!drv->probe ||
612                             (dev->device.devargs &&
613                             dev->device.devargs->policy == RTE_DEV_BLACKLISTED))
614                                 continue;
615
616                         if (probe_all ||
617                             (dev->device.devargs &&
618                             dev->device.devargs->policy ==
619                             RTE_DEV_WHITELISTED)) {
620                                 ret = drv->probe(drv, dev);
621                                 if (ret) {
622                                         DPAA_BUS_ERR("unable to probe:%s",
623                                                      dev->name);
624                                 } else {
625                                         dev->driver = drv;
626                                         dev->device.driver = &drv->driver;
627                                 }
628                         }
629                         break;
630                 }
631         }
632
633         /* Register DPAA mempool ops only if any DPAA device has
634          * been detected.
635          */
636         rte_mbuf_set_platform_mempool_ops(DPAA_MEMPOOL_OPS_NAME);
637
638         return 0;
639 }
640
641 static struct rte_device *
642 rte_dpaa_find_device(const struct rte_device *start, rte_dev_cmp_t cmp,
643                      const void *data)
644 {
645         struct rte_dpaa_device *dev;
646         const struct rte_dpaa_device *dstart;
647
648         /* find_device is called with 'data' as an opaque object - just call
649          * cmp with this and each device object on bus.
650          */
651
652         if (start != NULL) {
653                 dstart = RTE_DEV_TO_DPAA_CONST(start);
654                 dev = TAILQ_NEXT(dstart, next);
655         } else {
656                 dev = TAILQ_FIRST(&rte_dpaa_bus.device_list);
657         }
658
659         while (dev != NULL) {
660                 if (cmp(&dev->device, data) == 0) {
661                         DPAA_BUS_DEBUG("Found dev=(%s)\n", dev->device.name);
662                         return &dev->device;
663                 }
664                 dev = TAILQ_NEXT(dev, next);
665         }
666
667         DPAA_BUS_DEBUG("Unable to find any device\n");
668         return NULL;
669 }
670
671 /*
672  * Get iommu class of DPAA2 devices on the bus.
673  */
674 static enum rte_iova_mode
675 rte_dpaa_get_iommu_class(void)
676 {
677         if ((access(DPAA_DEV_PATH1, F_OK) != 0) &&
678             (access(DPAA_DEV_PATH2, F_OK) != 0)) {
679                 return RTE_IOVA_DC;
680         }
681         return RTE_IOVA_PA;
682 }
683
684 static int
685 dpaa_bus_plug(struct rte_device *dev __rte_unused)
686 {
687         /* No operation is performed while plugging the device */
688         return 0;
689 }
690
691 static int
692 dpaa_bus_unplug(struct rte_device *dev __rte_unused)
693 {
694         /* No operation is performed while unplugging the device */
695         return 0;
696 }
697
698 static void *
699 dpaa_bus_dev_iterate(const void *start, const char *str,
700                      const struct rte_dev_iterator *it __rte_unused)
701 {
702         const struct rte_dpaa_device *dstart;
703         struct rte_dpaa_device *dev;
704         char *dup, *dev_name = NULL;
705
706         /* Expectation is that device would be name=device_name */
707         if (strncmp(str, "name=", 5) != 0) {
708                 DPAA_BUS_DEBUG("Invalid device string (%s)\n", str);
709                 return NULL;
710         }
711
712         /* Now that name=device_name format is available, split */
713         dup = strdup(str);
714         dev_name = dup + strlen("name=");
715
716         if (start != NULL) {
717                 dstart = RTE_DEV_TO_DPAA_CONST(start);
718                 dev = TAILQ_NEXT(dstart, next);
719         } else {
720                 dev = TAILQ_FIRST(&rte_dpaa_bus.device_list);
721         }
722
723         while (dev != NULL) {
724                 if (strcmp(dev->device.name, dev_name) == 0) {
725                         free(dup);
726                         return &dev->device;
727                 }
728                 dev = TAILQ_NEXT(dev, next);
729         }
730
731         free(dup);
732         return NULL;
733 }
734
735 static struct rte_dpaa_bus rte_dpaa_bus = {
736         .bus = {
737                 .scan = rte_dpaa_bus_scan,
738                 .probe = rte_dpaa_bus_probe,
739                 .parse = rte_dpaa_bus_parse,
740                 .find_device = rte_dpaa_find_device,
741                 .get_iommu_class = rte_dpaa_get_iommu_class,
742                 .plug = dpaa_bus_plug,
743                 .unplug = dpaa_bus_unplug,
744                 .dev_iterate = dpaa_bus_dev_iterate,
745         },
746         .device_list = TAILQ_HEAD_INITIALIZER(rte_dpaa_bus.device_list),
747         .driver_list = TAILQ_HEAD_INITIALIZER(rte_dpaa_bus.driver_list),
748         .device_count = 0,
749 };
750
751 RTE_REGISTER_BUS(FSL_DPAA_BUS_NAME, rte_dpaa_bus.bus);
752
753 RTE_INIT(dpaa_init_log)
754 {
755         dpaa_logtype_bus = rte_log_register("bus.dpaa");
756         if (dpaa_logtype_bus >= 0)
757                 rte_log_set_level(dpaa_logtype_bus, RTE_LOG_NOTICE);
758 }