net/ice/base: fix NVGRE switch rule programming
[dpdk.git] / drivers / bus / fslmc / fslmc_vfio.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  *
3  *   Copyright (c) 2015-2016 Freescale Semiconductor, Inc. All rights reserved.
4  *   Copyright 2016-2019 NXP
5  *
6  */
7
8 #include <unistd.h>
9 #include <stdio.h>
10 #include <sys/types.h>
11 #include <string.h>
12 #include <stdlib.h>
13 #include <fcntl.h>
14 #include <errno.h>
15 #include <sys/ioctl.h>
16 #include <sys/stat.h>
17 #include <sys/mman.h>
18 #include <sys/vfs.h>
19 #include <libgen.h>
20 #include <dirent.h>
21 #include <sys/eventfd.h>
22
23 #include <eal_filesystem.h>
24 #include <rte_mbuf.h>
25 #include <rte_ethdev_driver.h>
26 #include <rte_malloc.h>
27 #include <rte_memcpy.h>
28 #include <rte_string_fns.h>
29 #include <rte_cycles.h>
30 #include <rte_kvargs.h>
31 #include <rte_dev.h>
32 #include <rte_bus.h>
33 #include <rte_eal_memconfig.h>
34
35 #include "rte_fslmc.h"
36 #include "fslmc_vfio.h"
37 #include "fslmc_logs.h"
38 #include <mc/fsl_dpmng.h>
39
40 #include "portal/dpaa2_hw_pvt.h"
41 #include "portal/dpaa2_hw_dpio.h"
42
43 #define FSLMC_CONTAINER_MAX_LEN 8 /**< Of the format dprc.XX */
44
45 /* Number of VFIO containers & groups with in */
46 static struct fslmc_vfio_group vfio_group;
47 static struct fslmc_vfio_container vfio_container;
48 static int container_device_fd;
49 char *fslmc_container;
50 static int fslmc_iommu_type;
51 static uint32_t *msi_intr_vaddr;
52 void *(*rte_mcp_ptr_list);
53
54 static struct rte_dpaa2_object_list dpaa2_obj_list =
55         TAILQ_HEAD_INITIALIZER(dpaa2_obj_list);
56
57 /*register a fslmc bus based dpaa2 driver */
58 void
59 rte_fslmc_object_register(struct rte_dpaa2_object *object)
60 {
61         RTE_VERIFY(object);
62
63         TAILQ_INSERT_TAIL(&dpaa2_obj_list, object, next);
64 }
65
66 int
67 fslmc_get_container_group(int *groupid)
68 {
69         int ret;
70         char *container;
71
72         if (!fslmc_container) {
73                 container = getenv("DPRC");
74                 if (container == NULL) {
75                         DPAA2_BUS_DEBUG("DPAA2: DPRC not available");
76                         return -EINVAL;
77                 }
78
79                 if (strlen(container) >= FSLMC_CONTAINER_MAX_LEN) {
80                         DPAA2_BUS_ERR("Invalid container name: %s", container);
81                         return -1;
82                 }
83
84                 fslmc_container = strdup(container);
85                 if (!fslmc_container) {
86                         DPAA2_BUS_ERR("Mem alloc failure; Container name");
87                         return -ENOMEM;
88                 }
89         }
90
91         fslmc_iommu_type = (rte_vfio_noiommu_is_enabled() == 1) ?
92                 RTE_VFIO_NOIOMMU : VFIO_TYPE1_IOMMU;
93
94         /* get group number */
95         ret = rte_vfio_get_group_num(SYSFS_FSL_MC_DEVICES,
96                                      fslmc_container, groupid);
97         if (ret <= 0) {
98                 DPAA2_BUS_ERR("Unable to find %s IOMMU group", fslmc_container);
99                 return -1;
100         }
101
102         DPAA2_BUS_DEBUG("Container: %s has VFIO iommu group id = %d",
103                         fslmc_container, *groupid);
104
105         return 0;
106 }
107
108 static int
109 vfio_connect_container(void)
110 {
111         int fd, ret;
112
113         if (vfio_container.used) {
114                 DPAA2_BUS_DEBUG("No container available");
115                 return -1;
116         }
117
118         /* Try connecting to vfio container if already created */
119         if (!ioctl(vfio_group.fd, VFIO_GROUP_SET_CONTAINER,
120                 &vfio_container.fd)) {
121                 DPAA2_BUS_DEBUG(
122                     "Container pre-exists with FD[0x%x] for this group",
123                     vfio_container.fd);
124                 vfio_group.container = &vfio_container;
125                 return 0;
126         }
127
128         /* Opens main vfio file descriptor which represents the "container" */
129         fd = rte_vfio_get_container_fd();
130         if (fd < 0) {
131                 DPAA2_BUS_ERR("Failed to open VFIO container");
132                 return -errno;
133         }
134
135         /* Check whether support for SMMU type IOMMU present or not */
136         if (ioctl(fd, VFIO_CHECK_EXTENSION, fslmc_iommu_type)) {
137                 /* Connect group to container */
138                 ret = ioctl(vfio_group.fd, VFIO_GROUP_SET_CONTAINER, &fd);
139                 if (ret) {
140                         DPAA2_BUS_ERR("Failed to setup group container");
141                         close(fd);
142                         return -errno;
143                 }
144
145                 ret = ioctl(fd, VFIO_SET_IOMMU, fslmc_iommu_type);
146                 if (ret) {
147                         DPAA2_BUS_ERR("Failed to setup VFIO iommu");
148                         close(fd);
149                         return -errno;
150                 }
151         } else {
152                 DPAA2_BUS_ERR("No supported IOMMU available");
153                 close(fd);
154                 return -EINVAL;
155         }
156
157         vfio_container.used = 1;
158         vfio_container.fd = fd;
159         vfio_container.group = &vfio_group;
160         vfio_group.container = &vfio_container;
161
162         return 0;
163 }
164
165 static int vfio_map_irq_region(struct fslmc_vfio_group *group)
166 {
167         int ret;
168         unsigned long *vaddr = NULL;
169         struct vfio_iommu_type1_dma_map map = {
170                 .argsz = sizeof(map),
171                 .flags = VFIO_DMA_MAP_FLAG_READ | VFIO_DMA_MAP_FLAG_WRITE,
172                 .vaddr = 0x6030000,
173                 .iova = 0x6030000,
174                 .size = 0x1000,
175         };
176
177         vaddr = (unsigned long *)mmap(NULL, 0x1000, PROT_WRITE |
178                 PROT_READ, MAP_SHARED, container_device_fd, 0x6030000);
179         if (vaddr == MAP_FAILED) {
180                 DPAA2_BUS_INFO("Unable to map region (errno = %d)", errno);
181                 return -errno;
182         }
183
184         msi_intr_vaddr = (uint32_t *)((char *)(vaddr) + 64);
185         map.vaddr = (unsigned long)vaddr;
186         ret = ioctl(group->container->fd, VFIO_IOMMU_MAP_DMA, &map);
187         if (ret == 0)
188                 return 0;
189
190         DPAA2_BUS_ERR("Unable to map DMA address (errno = %d)", errno);
191         return -errno;
192 }
193
194 static int fslmc_map_dma(uint64_t vaddr, rte_iova_t iovaddr, size_t len);
195 static int fslmc_unmap_dma(uint64_t vaddr, rte_iova_t iovaddr, size_t len);
196
197 static void
198 fslmc_memevent_cb(enum rte_mem_event type, const void *addr, size_t len,
199                 void *arg __rte_unused)
200 {
201         struct rte_memseg_list *msl;
202         struct rte_memseg *ms;
203         size_t cur_len = 0, map_len = 0;
204         uint64_t virt_addr;
205         rte_iova_t iova_addr;
206         int ret;
207
208         msl = rte_mem_virt2memseg_list(addr);
209
210         while (cur_len < len) {
211                 const void *va = RTE_PTR_ADD(addr, cur_len);
212
213                 ms = rte_mem_virt2memseg(va, msl);
214                 iova_addr = ms->iova;
215                 virt_addr = ms->addr_64;
216                 map_len = ms->len;
217
218                 DPAA2_BUS_DEBUG("Request for %s, va=%p, "
219                                 "virt_addr=0x%" PRIx64 ", "
220                                 "iova=0x%" PRIx64 ", map_len=%zu",
221                                 type == RTE_MEM_EVENT_ALLOC ?
222                                         "alloc" : "dealloc",
223                                 va, virt_addr, iova_addr, map_len);
224
225                 /* iova_addr may be set to RTE_BAD_IOVA */
226                 if (iova_addr == RTE_BAD_IOVA) {
227                         DPAA2_BUS_DEBUG("Segment has invalid iova, skipping\n");
228                         cur_len += map_len;
229                         continue;
230                 }
231
232                 if (type == RTE_MEM_EVENT_ALLOC)
233                         ret = fslmc_map_dma(virt_addr, iova_addr, map_len);
234                 else
235                         ret = fslmc_unmap_dma(virt_addr, iova_addr, map_len);
236
237                 if (ret != 0) {
238                         DPAA2_BUS_ERR("DMA Mapping/Unmapping failed. "
239                                         "Map=%d, addr=%p, len=%zu, err:(%d)",
240                                         type, va, map_len, ret);
241                         return;
242                 }
243
244                 cur_len += map_len;
245         }
246
247         if (type == RTE_MEM_EVENT_ALLOC)
248                 DPAA2_BUS_DEBUG("Total Mapped: addr=%p, len=%zu",
249                                 addr, len);
250         else
251                 DPAA2_BUS_DEBUG("Total Unmapped: addr=%p, len=%zu",
252                                 addr, len);
253 }
254
255 static int
256 fslmc_map_dma(uint64_t vaddr, rte_iova_t iovaddr __rte_unused, size_t len)
257 {
258         struct fslmc_vfio_group *group;
259         struct vfio_iommu_type1_dma_map dma_map = {
260                 .argsz = sizeof(struct vfio_iommu_type1_dma_map),
261                 .flags = VFIO_DMA_MAP_FLAG_READ | VFIO_DMA_MAP_FLAG_WRITE,
262         };
263         int ret;
264
265         if (fslmc_iommu_type == RTE_VFIO_NOIOMMU) {
266                 DPAA2_BUS_DEBUG("Running in NOIOMMU mode");
267                 return 0;
268         }
269
270         dma_map.size = len;
271         dma_map.vaddr = vaddr;
272
273 #ifdef RTE_LIBRTE_DPAA2_USE_PHYS_IOVA
274         dma_map.iova = iovaddr;
275 #else
276         dma_map.iova = dma_map.vaddr;
277 #endif
278
279         /* SET DMA MAP for IOMMU */
280         group = &vfio_group;
281
282         if (!group->container) {
283                 DPAA2_BUS_ERR("Container is not connected ");
284                 return -1;
285         }
286
287         DPAA2_BUS_DEBUG("--> Map address: 0x%"PRIx64", size: %"PRIu64"",
288                         (uint64_t)dma_map.vaddr, (uint64_t)dma_map.size);
289         ret = ioctl(group->container->fd, VFIO_IOMMU_MAP_DMA, &dma_map);
290         if (ret) {
291                 DPAA2_BUS_ERR("VFIO_IOMMU_MAP_DMA API(errno = %d)",
292                                 errno);
293                 return -1;
294         }
295
296         return 0;
297 }
298
299 static int
300 fslmc_unmap_dma(uint64_t vaddr, uint64_t iovaddr __rte_unused, size_t len)
301 {
302         struct fslmc_vfio_group *group;
303         struct vfio_iommu_type1_dma_unmap dma_unmap = {
304                 .argsz = sizeof(struct vfio_iommu_type1_dma_unmap),
305                 .flags = 0,
306         };
307         int ret;
308
309         if (fslmc_iommu_type == RTE_VFIO_NOIOMMU) {
310                 DPAA2_BUS_DEBUG("Running in NOIOMMU mode");
311                 return 0;
312         }
313
314         dma_unmap.size = len;
315         dma_unmap.iova = vaddr;
316
317         /* SET DMA MAP for IOMMU */
318         group = &vfio_group;
319
320         if (!group->container) {
321                 DPAA2_BUS_ERR("Container is not connected ");
322                 return -1;
323         }
324
325         DPAA2_BUS_DEBUG("--> Unmap address: 0x%"PRIx64", size: %"PRIu64"",
326                         (uint64_t)dma_unmap.iova, (uint64_t)dma_unmap.size);
327         ret = ioctl(group->container->fd, VFIO_IOMMU_UNMAP_DMA, &dma_unmap);
328         if (ret) {
329                 DPAA2_BUS_ERR("VFIO_IOMMU_UNMAP_DMA API(errno = %d)",
330                                 errno);
331                 return -1;
332         }
333
334         return 0;
335 }
336
337 static int
338 fslmc_dmamap_seg(const struct rte_memseg_list *msl __rte_unused,
339                 const struct rte_memseg *ms, void *arg)
340 {
341         int *n_segs = arg;
342         int ret;
343
344         /* if IOVA address is invalid, skip */
345         if (ms->iova == RTE_BAD_IOVA)
346                 return 0;
347
348         ret = fslmc_map_dma(ms->addr_64, ms->iova, ms->len);
349         if (ret)
350                 DPAA2_BUS_ERR("Unable to VFIO map (addr=%p, len=%zu)",
351                                 ms->addr, ms->len);
352         else
353                 (*n_segs)++;
354
355         return ret;
356 }
357
358 int
359 rte_fslmc_vfio_mem_dmamap(uint64_t vaddr, uint64_t iova, uint64_t size)
360 {
361         int ret;
362         struct fslmc_vfio_group *group;
363         struct vfio_iommu_type1_dma_map dma_map = {
364                 .argsz = sizeof(struct vfio_iommu_type1_dma_map),
365                 .flags = VFIO_DMA_MAP_FLAG_READ | VFIO_DMA_MAP_FLAG_WRITE,
366         };
367
368         if (fslmc_iommu_type == RTE_VFIO_NOIOMMU) {
369                 DPAA2_BUS_DEBUG("Running in NOIOMMU mode");
370                 return 0;
371         }
372
373         /* SET DMA MAP for IOMMU */
374         group = &vfio_group;
375         if (!group->container) {
376                 DPAA2_BUS_ERR("Container is not connected");
377                 return -1;
378         }
379
380         dma_map.size = size;
381         dma_map.vaddr = vaddr;
382         dma_map.iova = iova;
383
384         DPAA2_BUS_DEBUG("VFIOdmamap 0x%"PRIx64":0x%"PRIx64",size 0x%"PRIx64"\n",
385                         (uint64_t)dma_map.vaddr, (uint64_t)dma_map.iova,
386                         (uint64_t)dma_map.size);
387         ret = ioctl(group->container->fd, VFIO_IOMMU_MAP_DMA,
388                     &dma_map);
389         if (ret) {
390                 printf("Unable to map DMA address (errno = %d)\n",
391                         errno);
392                 return ret;
393         }
394
395         return 0;
396 }
397
398 int rte_fslmc_vfio_dmamap(void)
399 {
400         int i = 0, ret;
401
402         /* Lock before parsing and registering callback to memory subsystem */
403         rte_mcfg_mem_read_lock();
404
405         if (rte_memseg_walk(fslmc_dmamap_seg, &i) < 0) {
406                 rte_mcfg_mem_read_unlock();
407                 return -1;
408         }
409
410         ret = rte_mem_event_callback_register("fslmc_memevent_clb",
411                         fslmc_memevent_cb, NULL);
412         if (ret && rte_errno == ENOTSUP)
413                 DPAA2_BUS_DEBUG("Memory event callbacks not supported");
414         else if (ret)
415                 DPAA2_BUS_DEBUG("Unable to install memory handler");
416         else
417                 DPAA2_BUS_DEBUG("Installed memory callback handler");
418
419         DPAA2_BUS_DEBUG("Total %d segments found.", i);
420
421         /* TODO - This is a W.A. as VFIO currently does not add the mapping of
422          * the interrupt region to SMMU. This should be removed once the
423          * support is added in the Kernel.
424          */
425         vfio_map_irq_region(&vfio_group);
426
427         /* Existing segments have been mapped and memory callback for hotplug
428          * has been installed.
429          */
430         rte_mcfg_mem_read_unlock();
431
432         return 0;
433 }
434
435 static int
436 fslmc_vfio_setup_device(const char *sysfs_base, const char *dev_addr,
437                 int *vfio_dev_fd, struct vfio_device_info *device_info)
438 {
439         struct vfio_group_status group_status = {
440                         .argsz = sizeof(group_status)
441         };
442         int vfio_group_fd, vfio_container_fd, iommu_group_no, ret;
443
444         /* get group number */
445         ret = rte_vfio_get_group_num(sysfs_base, dev_addr, &iommu_group_no);
446         if (ret < 0)
447                 return -1;
448
449         /* get the actual group fd */
450         vfio_group_fd = rte_vfio_get_group_fd(iommu_group_no);
451         if (vfio_group_fd < 0)
452                 return -1;
453
454         /* if group_fd == 0, that means the device isn't managed by VFIO */
455         if (vfio_group_fd == 0) {
456                 RTE_LOG(WARNING, EAL, " %s not managed by VFIO driver, skipping\n",
457                                 dev_addr);
458                 return 1;
459         }
460
461         /* Opens main vfio file descriptor which represents the "container" */
462         vfio_container_fd = rte_vfio_get_container_fd();
463         if (vfio_container_fd < 0) {
464                 DPAA2_BUS_ERR("Failed to open VFIO container");
465                 return -errno;
466         }
467
468         /* check if the group is viable */
469         ret = ioctl(vfio_group_fd, VFIO_GROUP_GET_STATUS, &group_status);
470         if (ret) {
471                 DPAA2_BUS_ERR("  %s cannot get group status, "
472                                 "error %i (%s)\n", dev_addr,
473                                 errno, strerror(errno));
474                 close(vfio_group_fd);
475                 rte_vfio_clear_group(vfio_group_fd);
476                 return -1;
477         } else if (!(group_status.flags & VFIO_GROUP_FLAGS_VIABLE)) {
478                 DPAA2_BUS_ERR("  %s VFIO group is not viable!\n", dev_addr);
479                 close(vfio_group_fd);
480                 rte_vfio_clear_group(vfio_group_fd);
481                 return -1;
482         }
483         /* At this point, we know that this group is viable (meaning,
484          * all devices are either bound to VFIO or not bound to anything)
485          */
486
487         /* check if group does not have a container yet */
488         if (!(group_status.flags & VFIO_GROUP_FLAGS_CONTAINER_SET)) {
489
490                 /* add group to a container */
491                 ret = ioctl(vfio_group_fd, VFIO_GROUP_SET_CONTAINER,
492                                 &vfio_container_fd);
493                 if (ret) {
494                         DPAA2_BUS_ERR("  %s cannot add VFIO group to container, "
495                                         "error %i (%s)\n", dev_addr,
496                                         errno, strerror(errno));
497                         close(vfio_group_fd);
498                         close(vfio_container_fd);
499                         rte_vfio_clear_group(vfio_group_fd);
500                         return -1;
501                 }
502
503                 /*
504                  * set an IOMMU type for container
505                  *
506                  */
507                 if (ioctl(vfio_container_fd, VFIO_CHECK_EXTENSION,
508                           fslmc_iommu_type)) {
509                         ret = ioctl(vfio_container_fd, VFIO_SET_IOMMU,
510                                     fslmc_iommu_type);
511                         if (ret) {
512                                 DPAA2_BUS_ERR("Failed to setup VFIO iommu");
513                                 close(vfio_group_fd);
514                                 close(vfio_container_fd);
515                                 return -errno;
516                         }
517                 } else {
518                         DPAA2_BUS_ERR("No supported IOMMU available");
519                         close(vfio_group_fd);
520                         close(vfio_container_fd);
521                         return -EINVAL;
522                 }
523         }
524
525         /* get a file descriptor for the device */
526         *vfio_dev_fd = ioctl(vfio_group_fd, VFIO_GROUP_GET_DEVICE_FD, dev_addr);
527         if (*vfio_dev_fd < 0) {
528                 /* if we cannot get a device fd, this implies a problem with
529                  * the VFIO group or the container not having IOMMU configured.
530                  */
531
532                 DPAA2_BUS_WARN("Getting a vfio_dev_fd for %s failed", dev_addr);
533                 close(vfio_group_fd);
534                 close(vfio_container_fd);
535                 rte_vfio_clear_group(vfio_group_fd);
536                 return -1;
537         }
538
539         /* test and setup the device */
540         ret = ioctl(*vfio_dev_fd, VFIO_DEVICE_GET_INFO, device_info);
541         if (ret) {
542                 DPAA2_BUS_ERR("  %s cannot get device info, error %i (%s)",
543                                 dev_addr, errno, strerror(errno));
544                 close(*vfio_dev_fd);
545                 close(vfio_group_fd);
546                 close(vfio_container_fd);
547                 rte_vfio_clear_group(vfio_group_fd);
548                 return -1;
549         }
550
551         return 0;
552 }
553
554 static intptr_t vfio_map_mcp_obj(const char *mcp_obj)
555 {
556         intptr_t v_addr = (intptr_t)MAP_FAILED;
557         int32_t ret, mc_fd;
558         struct vfio_group_status status = { .argsz = sizeof(status) };
559
560         struct vfio_device_info d_info = { .argsz = sizeof(d_info) };
561         struct vfio_region_info reg_info = { .argsz = sizeof(reg_info) };
562
563         fslmc_vfio_setup_device(SYSFS_FSL_MC_DEVICES, mcp_obj,
564                         &mc_fd, &d_info);
565
566         /* getting device region info*/
567         ret = ioctl(mc_fd, VFIO_DEVICE_GET_REGION_INFO, &reg_info);
568         if (ret < 0) {
569                 DPAA2_BUS_ERR("Error in VFIO getting REGION_INFO");
570                 goto MC_FAILURE;
571         }
572
573         v_addr = (size_t)mmap(NULL, reg_info.size,
574                 PROT_WRITE | PROT_READ, MAP_SHARED,
575                 mc_fd, reg_info.offset);
576
577 MC_FAILURE:
578         close(mc_fd);
579
580         return v_addr;
581 }
582
583 #define IRQ_SET_BUF_LEN  (sizeof(struct vfio_irq_set) + sizeof(int))
584
585 int rte_dpaa2_intr_enable(struct rte_intr_handle *intr_handle, int index)
586 {
587         int len, ret;
588         char irq_set_buf[IRQ_SET_BUF_LEN];
589         struct vfio_irq_set *irq_set;
590         int *fd_ptr;
591
592         len = sizeof(irq_set_buf);
593
594         irq_set = (struct vfio_irq_set *)irq_set_buf;
595         irq_set->argsz = len;
596         irq_set->count = 1;
597         irq_set->flags =
598                 VFIO_IRQ_SET_DATA_EVENTFD | VFIO_IRQ_SET_ACTION_TRIGGER;
599         irq_set->index = index;
600         irq_set->start = 0;
601         fd_ptr = (int *)&irq_set->data;
602         *fd_ptr = intr_handle->fd;
603
604         ret = ioctl(intr_handle->vfio_dev_fd, VFIO_DEVICE_SET_IRQS, irq_set);
605         if (ret) {
606                 DPAA2_BUS_ERR("Error:dpaa2 SET IRQs fd=%d, err = %d(%s)",
607                               intr_handle->fd, errno, strerror(errno));
608                 return ret;
609         }
610
611         return ret;
612 }
613
614 int rte_dpaa2_intr_disable(struct rte_intr_handle *intr_handle, int index)
615 {
616         struct vfio_irq_set *irq_set;
617         char irq_set_buf[IRQ_SET_BUF_LEN];
618         int len, ret;
619
620         len = sizeof(struct vfio_irq_set);
621
622         irq_set = (struct vfio_irq_set *)irq_set_buf;
623         irq_set->argsz = len;
624         irq_set->flags = VFIO_IRQ_SET_DATA_NONE | VFIO_IRQ_SET_ACTION_TRIGGER;
625         irq_set->index = index;
626         irq_set->start = 0;
627         irq_set->count = 0;
628
629         ret = ioctl(intr_handle->vfio_dev_fd, VFIO_DEVICE_SET_IRQS, irq_set);
630         if (ret)
631                 DPAA2_BUS_ERR(
632                         "Error disabling dpaa2 interrupts for fd %d",
633                         intr_handle->fd);
634
635         return ret;
636 }
637
638 /* set up interrupt support (but not enable interrupts) */
639 int
640 rte_dpaa2_vfio_setup_intr(struct rte_intr_handle *intr_handle,
641                           int vfio_dev_fd,
642                           int num_irqs)
643 {
644         int i, ret;
645
646         /* start from MSI-X interrupt type */
647         for (i = 0; i < num_irqs; i++) {
648                 struct vfio_irq_info irq_info = { .argsz = sizeof(irq_info) };
649                 int fd = -1;
650
651                 irq_info.index = i;
652
653                 ret = ioctl(vfio_dev_fd, VFIO_DEVICE_GET_IRQ_INFO, &irq_info);
654                 if (ret < 0) {
655                         DPAA2_BUS_ERR("Cannot get IRQ(%d) info, error %i (%s)",
656                                       i, errno, strerror(errno));
657                         return -1;
658                 }
659
660                 /* if this vector cannot be used with eventfd,
661                  * fail if we explicitly
662                  * specified interrupt type, otherwise continue
663                  */
664                 if ((irq_info.flags & VFIO_IRQ_INFO_EVENTFD) == 0)
665                         continue;
666
667                 /* set up an eventfd for interrupts */
668                 fd = eventfd(0, EFD_NONBLOCK | EFD_CLOEXEC);
669                 if (fd < 0) {
670                         DPAA2_BUS_ERR("Cannot set up eventfd, error %i (%s)",
671                                       errno, strerror(errno));
672                         return -1;
673                 }
674
675                 intr_handle->fd = fd;
676                 intr_handle->type = RTE_INTR_HANDLE_VFIO_MSI;
677                 intr_handle->vfio_dev_fd = vfio_dev_fd;
678
679                 return 0;
680         }
681
682         /* if we're here, we haven't found a suitable interrupt vector */
683         return -1;
684 }
685
686 /*
687  * fslmc_process_iodevices for processing only IO (ETH, CRYPTO, and possibly
688  * EVENT) devices.
689  */
690 static int
691 fslmc_process_iodevices(struct rte_dpaa2_device *dev)
692 {
693         int dev_fd;
694         struct vfio_device_info device_info = { .argsz = sizeof(device_info) };
695         struct rte_dpaa2_object *object = NULL;
696
697         fslmc_vfio_setup_device(SYSFS_FSL_MC_DEVICES, dev->device.name,
698                         &dev_fd, &device_info);
699
700         switch (dev->dev_type) {
701         case DPAA2_ETH:
702                 rte_dpaa2_vfio_setup_intr(&dev->intr_handle, dev_fd,
703                                           device_info.num_irqs);
704                 break;
705         case DPAA2_CON:
706         case DPAA2_IO:
707         case DPAA2_CI:
708         case DPAA2_BPOOL:
709         case DPAA2_DPRTC:
710         case DPAA2_MUX:
711                 TAILQ_FOREACH(object, &dpaa2_obj_list, next) {
712                         if (dev->dev_type == object->dev_type)
713                                 object->create(dev_fd, &device_info,
714                                                dev->object_id);
715                         else
716                                 continue;
717                 }
718                 break;
719         default:
720                 break;
721         }
722
723         DPAA2_BUS_LOG(DEBUG, "Device (%s) abstracted from VFIO",
724                       dev->device.name);
725         return 0;
726 }
727
728 static int
729 fslmc_process_mcp(struct rte_dpaa2_device *dev)
730 {
731         int ret;
732         intptr_t v_addr;
733         char *dev_name = NULL;
734         struct fsl_mc_io dpmng  = {0};
735         struct mc_version mc_ver_info = {0};
736
737         rte_mcp_ptr_list = malloc(sizeof(void *) * 1);
738         if (!rte_mcp_ptr_list) {
739                 DPAA2_BUS_ERR("Unable to allocate MC portal memory");
740                 ret = -ENOMEM;
741                 goto cleanup;
742         }
743
744         dev_name = strdup(dev->device.name);
745         if (!dev_name) {
746                 DPAA2_BUS_ERR("Unable to allocate MC device name memory");
747                 ret = -ENOMEM;
748                 goto cleanup;
749         }
750
751         v_addr = vfio_map_mcp_obj(dev->device.name);
752         if (v_addr == (intptr_t)MAP_FAILED) {
753                 DPAA2_BUS_ERR("Error mapping region (errno = %d)", errno);
754                 ret = -1;
755                 goto cleanup;
756         }
757
758         /* check the MC version compatibility */
759         dpmng.regs = (void *)v_addr;
760
761         /* In case of secondary processes, MC version check is no longer
762          * required.
763          */
764         if (rte_eal_process_type() == RTE_PROC_SECONDARY) {
765                 rte_mcp_ptr_list[0] = (void *)v_addr;
766                 return 0;
767         }
768
769         if (mc_get_version(&dpmng, CMD_PRI_LOW, &mc_ver_info)) {
770                 DPAA2_BUS_ERR("Unable to obtain MC version");
771                 ret = -1;
772                 goto cleanup;
773         }
774
775         if ((mc_ver_info.major != MC_VER_MAJOR) ||
776             (mc_ver_info.minor < MC_VER_MINOR)) {
777                 DPAA2_BUS_ERR("DPAA2 MC version not compatible!"
778                               " Expected %d.%d.x, Detected %d.%d.%d",
779                               MC_VER_MAJOR, MC_VER_MINOR,
780                               mc_ver_info.major, mc_ver_info.minor,
781                               mc_ver_info.revision);
782                 ret = -1;
783                 goto cleanup;
784         }
785         rte_mcp_ptr_list[0] = (void *)v_addr;
786
787         free(dev_name);
788         return 0;
789
790 cleanup:
791         if (dev_name)
792                 free(dev_name);
793
794         if (rte_mcp_ptr_list) {
795                 free(rte_mcp_ptr_list);
796                 rte_mcp_ptr_list = NULL;
797         }
798
799         return ret;
800 }
801
802 int
803 fslmc_vfio_process_group(void)
804 {
805         int ret;
806         int found_mportal = 0;
807         struct rte_dpaa2_device *dev, *dev_temp;
808
809         /* Search the MCP as that should be initialized first. */
810         TAILQ_FOREACH_SAFE(dev, &rte_fslmc_bus.device_list, next, dev_temp) {
811                 if (dev->dev_type == DPAA2_MPORTAL) {
812                         if (dev->device.devargs &&
813                             dev->device.devargs->policy == RTE_DEV_BLACKLISTED) {
814                                 DPAA2_BUS_LOG(DEBUG, "%s Blacklisted, skipping",
815                                               dev->device.name);
816                                 TAILQ_REMOVE(&rte_fslmc_bus.device_list,
817                                                 dev, next);
818                                 continue;
819                         }
820
821                         ret = fslmc_process_mcp(dev);
822                         if (ret) {
823                                 DPAA2_BUS_ERR("Unable to map MC Portal");
824                                 return -1;
825                         }
826                         if (!found_mportal)
827                                 found_mportal = 1;
828
829                         TAILQ_REMOVE(&rte_fslmc_bus.device_list, dev, next);
830                         free(dev);
831                         dev = NULL;
832                         /* Ideally there is only a single dpmcp, but in case
833                          * multiple exists, looping on remaining devices.
834                          */
835                 }
836         }
837
838         /* Cannot continue if there is not even a single mportal */
839         if (!found_mportal) {
840                 DPAA2_BUS_ERR("No MC Portal device found. Not continuing");
841                 return -1;
842         }
843
844         TAILQ_FOREACH_SAFE(dev, &rte_fslmc_bus.device_list, next, dev_temp) {
845                 if (dev->device.devargs &&
846                     dev->device.devargs->policy == RTE_DEV_BLACKLISTED) {
847                         DPAA2_BUS_LOG(DEBUG, "%s Blacklisted, skipping",
848                                       dev->device.name);
849                         TAILQ_REMOVE(&rte_fslmc_bus.device_list, dev, next);
850                         continue;
851                 }
852                 switch (dev->dev_type) {
853                 case DPAA2_ETH:
854                 case DPAA2_CRYPTO:
855                 case DPAA2_QDMA:
856                         ret = fslmc_process_iodevices(dev);
857                         if (ret) {
858                                 DPAA2_BUS_DEBUG("Dev (%s) init failed",
859                                                 dev->device.name);
860                                 return ret;
861                         }
862                         break;
863                 case DPAA2_CON:
864                 case DPAA2_CI:
865                 case DPAA2_BPOOL:
866                 case DPAA2_DPRTC:
867                 case DPAA2_MUX:
868                         /* IN case of secondary processes, all control objects
869                          * like dpbp, dpcon, dpci are not initialized/required
870                          * - all of these are assumed to be initialized and made
871                          *   available by primary.
872                          */
873                         if (rte_eal_process_type() == RTE_PROC_SECONDARY)
874                                 continue;
875
876                         /* Call the object creation routine and remove the
877                          * device entry from device list
878                          */
879                         ret = fslmc_process_iodevices(dev);
880                         if (ret) {
881                                 DPAA2_BUS_DEBUG("Dev (%s) init failed",
882                                                 dev->device.name);
883                                 return -1;
884                         }
885
886                         break;
887                 case DPAA2_IO:
888                         ret = fslmc_process_iodevices(dev);
889                         if (ret) {
890                                 DPAA2_BUS_DEBUG("Dev (%s) init failed",
891                                                 dev->device.name);
892                                 return -1;
893                         }
894
895                         break;
896                 case DPAA2_UNKNOWN:
897                 default:
898                         /* Unknown - ignore */
899                         DPAA2_BUS_DEBUG("Found unknown device (%s)",
900                                         dev->device.name);
901                         TAILQ_REMOVE(&rte_fslmc_bus.device_list, dev, next);
902                         free(dev);
903                         dev = NULL;
904                 }
905         }
906
907         return 0;
908 }
909
910 int
911 fslmc_vfio_setup_group(void)
912 {
913         int groupid;
914         int ret;
915         struct vfio_group_status status = { .argsz = sizeof(status) };
916
917         /* if already done once */
918         if (container_device_fd)
919                 return 0;
920
921         ret = fslmc_get_container_group(&groupid);
922         if (ret)
923                 return ret;
924
925         /* In case this group was already opened, continue without any
926          * processing.
927          */
928         if (vfio_group.groupid == groupid) {
929                 DPAA2_BUS_ERR("groupid already exists %d", groupid);
930                 return 0;
931         }
932
933         /* Get the actual group fd */
934         ret = rte_vfio_get_group_fd(groupid);
935         if (ret < 0)
936                 return ret;
937         vfio_group.fd = ret;
938
939         /* Check group viability */
940         ret = ioctl(vfio_group.fd, VFIO_GROUP_GET_STATUS, &status);
941         if (ret) {
942                 DPAA2_BUS_ERR("VFIO error getting group status");
943                 close(vfio_group.fd);
944                 rte_vfio_clear_group(vfio_group.fd);
945                 return ret;
946         }
947
948         if (!(status.flags & VFIO_GROUP_FLAGS_VIABLE)) {
949                 DPAA2_BUS_ERR("VFIO group not viable");
950                 close(vfio_group.fd);
951                 rte_vfio_clear_group(vfio_group.fd);
952                 return -EPERM;
953         }
954         /* Since Group is VIABLE, Store the groupid */
955         vfio_group.groupid = groupid;
956
957         /* check if group does not have a container yet */
958         if (!(status.flags & VFIO_GROUP_FLAGS_CONTAINER_SET)) {
959                 /* Now connect this IOMMU group to given container */
960                 ret = vfio_connect_container();
961                 if (ret) {
962                         DPAA2_BUS_ERR(
963                                 "Error connecting container with groupid %d",
964                                 groupid);
965                         close(vfio_group.fd);
966                         rte_vfio_clear_group(vfio_group.fd);
967                         return ret;
968                 }
969         }
970
971         /* Get Device information */
972         ret = ioctl(vfio_group.fd, VFIO_GROUP_GET_DEVICE_FD, fslmc_container);
973         if (ret < 0) {
974                 DPAA2_BUS_ERR("Error getting device %s fd from group %d",
975                               fslmc_container, vfio_group.groupid);
976                 close(vfio_group.fd);
977                 rte_vfio_clear_group(vfio_group.fd);
978                 return ret;
979         }
980         container_device_fd = ret;
981         DPAA2_BUS_DEBUG("VFIO Container FD is [0x%X]",
982                         container_device_fd);
983
984         return 0;
985 }