vfio: move global config out of PCI files
[dpdk.git] / lib / librte_eal / linuxapp / eal / eal_vfio.c
1 /*-
2  *   BSD LICENSE
3  *
4  *   Copyright(c) 2010-2014 Intel Corporation. All rights reserved.
5  *   All rights reserved.
6  *
7  *   Redistribution and use in source and binary forms, with or without
8  *   modification, are permitted provided that the following conditions
9  *   are met:
10  *
11  *     * Redistributions of source code must retain the above copyright
12  *       notice, this list of conditions and the following disclaimer.
13  *     * Redistributions in binary form must reproduce the above copyright
14  *       notice, this list of conditions and the following disclaimer in
15  *       the documentation and/or other materials provided with the
16  *       distribution.
17  *     * Neither the name of Intel Corporation nor the names of its
18  *       contributors may be used to endorse or promote products derived
19  *       from this software without specific prior written permission.
20  *
21  *   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22  *   "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23  *   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
24  *   A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
25  *   OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
26  *   SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
27  *   LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
28  *   DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
29  *   THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
30  *   (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
31  *   OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32  */
33
34 #include <string.h>
35 #include <fcntl.h>
36 #include <unistd.h>
37 #include <sys/ioctl.h>
38
39 #include <rte_log.h>
40 #include <rte_memory.h>
41 #include <rte_eal_memconfig.h>
42
43 #include "eal_filesystem.h"
44 #include "eal_vfio.h"
45 #include "eal_private.h"
46
47 #ifdef VFIO_PRESENT
48
49 /* per-process VFIO config */
50 static struct vfio_config vfio_cfg;
51
52 int
53 vfio_get_group_fd(int iommu_group_no)
54 {
55         int i;
56         int vfio_group_fd;
57         char filename[PATH_MAX];
58
59         /* check if we already have the group descriptor open */
60         for (i = 0; i < vfio_cfg.vfio_group_idx; i++)
61                 if (vfio_cfg.vfio_groups[i].group_no == iommu_group_no)
62                         return vfio_cfg.vfio_groups[i].fd;
63
64         /* if primary, try to open the group */
65         if (internal_config.process_type == RTE_PROC_PRIMARY) {
66                 /* try regular group format */
67                 snprintf(filename, sizeof(filename),
68                                  VFIO_GROUP_FMT, iommu_group_no);
69                 vfio_group_fd = open(filename, O_RDWR);
70                 if (vfio_group_fd < 0) {
71                         /* if file not found, it's not an error */
72                         if (errno != ENOENT) {
73                                 RTE_LOG(ERR, EAL, "Cannot open %s: %s\n", filename,
74                                                 strerror(errno));
75                                 return -1;
76                         }
77
78                         /* special case: try no-IOMMU path as well */
79                         snprintf(filename, sizeof(filename),
80                                         VFIO_NOIOMMU_GROUP_FMT, iommu_group_no);
81                         vfio_group_fd = open(filename, O_RDWR);
82                         if (vfio_group_fd < 0) {
83                                 if (errno != ENOENT) {
84                                         RTE_LOG(ERR, EAL, "Cannot open %s: %s\n", filename,
85                                                         strerror(errno));
86                                         return -1;
87                                 }
88                                 return 0;
89                         }
90                         /* noiommu group found */
91                 }
92
93                 /* if the fd is valid, create a new group for it */
94                 if (vfio_cfg.vfio_group_idx == VFIO_MAX_GROUPS) {
95                         RTE_LOG(ERR, EAL, "Maximum number of VFIO groups reached!\n");
96                         close(vfio_group_fd);
97                         return -1;
98                 }
99                 vfio_cfg.vfio_groups[vfio_cfg.vfio_group_idx].group_no = iommu_group_no;
100                 vfio_cfg.vfio_groups[vfio_cfg.vfio_group_idx].fd = vfio_group_fd;
101                 return vfio_group_fd;
102         }
103         /* if we're in a secondary process, request group fd from the primary
104          * process via our socket
105          */
106         else {
107                 int socket_fd, ret;
108
109                 socket_fd = vfio_mp_sync_connect_to_primary();
110
111                 if (socket_fd < 0) {
112                         RTE_LOG(ERR, EAL, "  cannot connect to primary process!\n");
113                         return -1;
114                 }
115                 if (vfio_mp_sync_send_request(socket_fd, SOCKET_REQ_GROUP) < 0) {
116                         RTE_LOG(ERR, EAL, "  cannot request container fd!\n");
117                         close(socket_fd);
118                         return -1;
119                 }
120                 if (vfio_mp_sync_send_request(socket_fd, iommu_group_no) < 0) {
121                         RTE_LOG(ERR, EAL, "  cannot send group number!\n");
122                         close(socket_fd);
123                         return -1;
124                 }
125                 ret = vfio_mp_sync_receive_request(socket_fd);
126                 switch (ret) {
127                 case SOCKET_NO_FD:
128                         close(socket_fd);
129                         return 0;
130                 case SOCKET_OK:
131                         vfio_group_fd = vfio_mp_sync_receive_fd(socket_fd);
132                         /* if we got the fd, return it */
133                         if (vfio_group_fd > 0) {
134                                 close(socket_fd);
135                                 return vfio_group_fd;
136                         }
137                         /* fall-through on error */
138                 default:
139                         RTE_LOG(ERR, EAL, "  cannot get container fd!\n");
140                         close(socket_fd);
141                         return -1;
142                 }
143         }
144         return -1;
145 }
146
147 static void
148 clear_current_group(void)
149 {
150         vfio_cfg.vfio_groups[vfio_cfg.vfio_group_idx].group_no = 0;
151         vfio_cfg.vfio_groups[vfio_cfg.vfio_group_idx].fd = -1;
152 }
153
154 int vfio_setup_device(const char *sysfs_base, const char *dev_addr,
155                 int *vfio_dev_fd, struct vfio_device_info *device_info)
156 {
157         struct vfio_group_status group_status = {
158                         .argsz = sizeof(group_status)
159         };
160         int vfio_group_fd;
161         int iommu_group_no;
162         int ret;
163
164         /* get group number */
165         ret = vfio_get_group_no(sysfs_base, dev_addr, &iommu_group_no);
166         if (ret == 0) {
167                 RTE_LOG(WARNING, EAL, "  %s not managed by VFIO driver, skipping\n",
168                         dev_addr);
169                 return 1;
170         }
171
172         /* if negative, something failed */
173         if (ret < 0)
174                 return -1;
175
176         /* get the actual group fd */
177         vfio_group_fd = vfio_get_group_fd(iommu_group_no);
178         if (vfio_group_fd < 0)
179                 return -1;
180
181         /* store group fd */
182         vfio_cfg.vfio_groups[vfio_cfg.vfio_group_idx].group_no = iommu_group_no;
183         vfio_cfg.vfio_groups[vfio_cfg.vfio_group_idx].fd = vfio_group_fd;
184
185         /* if group_fd == 0, that means the device isn't managed by VFIO */
186         if (vfio_group_fd == 0) {
187                 RTE_LOG(WARNING, EAL, "  %s not managed by VFIO driver, skipping\n",
188                                 dev_addr);
189                 /* we store 0 as group fd to distinguish between existing but
190                  * unbound VFIO groups, and groups that don't exist at all.
191                  */
192                 vfio_cfg.vfio_group_idx++;
193                 return 1;
194         }
195
196         /*
197          * at this point, we know that this group is viable (meaning, all devices
198          * are either bound to VFIO or not bound to anything)
199          */
200
201         /* check if the group is viable */
202         ret = ioctl(vfio_group_fd, VFIO_GROUP_GET_STATUS, &group_status);
203         if (ret) {
204                 RTE_LOG(ERR, EAL, "  %s cannot get group status, "
205                                 "error %i (%s)\n", dev_addr, errno, strerror(errno));
206                 close(vfio_group_fd);
207                 clear_current_group();
208                 return -1;
209         } else if (!(group_status.flags & VFIO_GROUP_FLAGS_VIABLE)) {
210                 RTE_LOG(ERR, EAL, "  %s VFIO group is not viable!\n", dev_addr);
211                 close(vfio_group_fd);
212                 clear_current_group();
213                 return -1;
214         }
215
216         /* check if group does not have a container yet */
217         if (!(group_status.flags & VFIO_GROUP_FLAGS_CONTAINER_SET)) {
218
219                 /* add group to a container */
220                 ret = ioctl(vfio_group_fd, VFIO_GROUP_SET_CONTAINER,
221                                 &vfio_cfg.vfio_container_fd);
222                 if (ret) {
223                         RTE_LOG(ERR, EAL, "  %s cannot add VFIO group to container, "
224                                         "error %i (%s)\n", dev_addr, errno, strerror(errno));
225                         close(vfio_group_fd);
226                         clear_current_group();
227                         return -1;
228                 }
229                 /*
230                  * at this point we know that this group has been successfully
231                  * initialized, so we increment vfio_group_idx to indicate that we can
232                  * add new groups.
233                  */
234                 vfio_cfg.vfio_group_idx++;
235         }
236
237         /*
238          * pick an IOMMU type and set up DMA mappings for container
239          *
240          * needs to be done only once, only when at least one group is assigned to
241          * a container and only in primary process
242          */
243         if (internal_config.process_type == RTE_PROC_PRIMARY &&
244                         vfio_cfg.vfio_container_has_dma == 0) {
245                 /* select an IOMMU type which we will be using */
246                 const struct vfio_iommu_type *t =
247                                 vfio_set_iommu_type(vfio_cfg.vfio_container_fd);
248                 if (!t) {
249                         RTE_LOG(ERR, EAL, "  %s failed to select IOMMU type\n", dev_addr);
250                         return -1;
251                 }
252                 ret = t->dma_map_func(vfio_cfg.vfio_container_fd);
253                 if (ret) {
254                         RTE_LOG(ERR, EAL, "  %s DMA remapping failed, "
255                                         "error %i (%s)\n", dev_addr, errno, strerror(errno));
256                         return -1;
257                 }
258                 vfio_cfg.vfio_container_has_dma = 1;
259         }
260
261         /* get a file descriptor for the device */
262         *vfio_dev_fd = ioctl(vfio_group_fd, VFIO_GROUP_GET_DEVICE_FD, dev_addr);
263         if (*vfio_dev_fd < 0) {
264                 /* if we cannot get a device fd, this simply means that this
265                 * particular port is not bound to VFIO
266                 */
267                 RTE_LOG(WARNING, EAL, "  %s not managed by VFIO driver, skipping\n",
268                                 dev_addr);
269                 return 1;
270         }
271
272         /* test and setup the device */
273         ret = ioctl(*vfio_dev_fd, VFIO_DEVICE_GET_INFO, device_info);
274         if (ret) {
275                 RTE_LOG(ERR, EAL, "  %s cannot get device info, "
276                                 "error %i (%s)\n", dev_addr, errno, strerror(errno));
277                 close(*vfio_dev_fd);
278                 return -1;
279         }
280
281         return 0;
282 }
283
284 int
285 vfio_enable(const char *modname)
286 {
287         /* initialize group list */
288         int i;
289         int vfio_available;
290
291         for (i = 0; i < VFIO_MAX_GROUPS; i++) {
292                 vfio_cfg.vfio_groups[i].fd = -1;
293                 vfio_cfg.vfio_groups[i].group_no = -1;
294         }
295
296         /* inform the user that we are probing for VFIO */
297         RTE_LOG(INFO, EAL, "Probing VFIO support...\n");
298
299         /* check if vfio-pci module is loaded */
300         vfio_available = rte_eal_check_module(modname);
301
302         /* return error directly */
303         if (vfio_available == -1) {
304                 RTE_LOG(INFO, EAL, "Could not get loaded module details!\n");
305                 return -1;
306         }
307
308         /* return 0 if VFIO modules not loaded */
309         if (vfio_available == 0) {
310                 RTE_LOG(DEBUG, EAL, "VFIO modules not loaded, "
311                         "skipping VFIO support...\n");
312                 return 0;
313         }
314
315         vfio_cfg.vfio_container_fd = vfio_get_container_fd();
316
317         /* check if we have VFIO driver enabled */
318         if (vfio_cfg.vfio_container_fd != -1) {
319                 RTE_LOG(NOTICE, EAL, "VFIO support initialized\n");
320                 vfio_cfg.vfio_enabled = 1;
321         } else {
322                 RTE_LOG(NOTICE, EAL, "VFIO support could not be initialized\n");
323         }
324
325         return 0;
326 }
327
328 int
329 vfio_is_enabled(const char *modname)
330 {
331         const int mod_available = rte_eal_check_module(modname);
332         return vfio_cfg.vfio_enabled && mod_available;
333 }
334
335 const struct vfio_iommu_type *
336 vfio_set_iommu_type(int vfio_container_fd) {
337         unsigned idx;
338         for (idx = 0; idx < RTE_DIM(iommu_types); idx++) {
339                 const struct vfio_iommu_type *t = &iommu_types[idx];
340
341                 int ret = ioctl(vfio_container_fd, VFIO_SET_IOMMU,
342                                 t->type_id);
343                 if (!ret) {
344                         RTE_LOG(NOTICE, EAL, "  using IOMMU type %d (%s)\n",
345                                         t->type_id, t->name);
346                         return t;
347                 }
348                 /* not an error, there may be more supported IOMMU types */
349                 RTE_LOG(DEBUG, EAL, "  set IOMMU type %d (%s) failed, "
350                                 "error %i (%s)\n", t->type_id, t->name, errno,
351                                 strerror(errno));
352         }
353         /* if we didn't find a suitable IOMMU type, fail */
354         return NULL;
355 }
356
357 int
358 vfio_has_supported_extensions(int vfio_container_fd) {
359         int ret;
360         unsigned idx, n_extensions = 0;
361         for (idx = 0; idx < RTE_DIM(iommu_types); idx++) {
362                 const struct vfio_iommu_type *t = &iommu_types[idx];
363
364                 ret = ioctl(vfio_container_fd, VFIO_CHECK_EXTENSION,
365                                 t->type_id);
366                 if (ret < 0) {
367                         RTE_LOG(ERR, EAL, "  could not get IOMMU type, "
368                                 "error %i (%s)\n", errno,
369                                 strerror(errno));
370                         close(vfio_container_fd);
371                         return -1;
372                 } else if (ret == 1) {
373                         /* we found a supported extension */
374                         n_extensions++;
375                 }
376                 RTE_LOG(DEBUG, EAL, "  IOMMU type %d (%s) is %s\n",
377                                 t->type_id, t->name,
378                                 ret ? "supported" : "not supported");
379         }
380
381         /* if we didn't find any supported IOMMU types, fail */
382         if (!n_extensions) {
383                 close(vfio_container_fd);
384                 return -1;
385         }
386
387         return 0;
388 }
389
390 int
391 vfio_get_container_fd(void)
392 {
393         int ret, vfio_container_fd;
394
395         /* if we're in a primary process, try to open the container */
396         if (internal_config.process_type == RTE_PROC_PRIMARY) {
397                 vfio_container_fd = open(VFIO_CONTAINER_PATH, O_RDWR);
398                 if (vfio_container_fd < 0) {
399                         RTE_LOG(ERR, EAL, "  cannot open VFIO container, "
400                                         "error %i (%s)\n", errno, strerror(errno));
401                         return -1;
402                 }
403
404                 /* check VFIO API version */
405                 ret = ioctl(vfio_container_fd, VFIO_GET_API_VERSION);
406                 if (ret != VFIO_API_VERSION) {
407                         if (ret < 0)
408                                 RTE_LOG(ERR, EAL, "  could not get VFIO API version, "
409                                                 "error %i (%s)\n", errno, strerror(errno));
410                         else
411                                 RTE_LOG(ERR, EAL, "  unsupported VFIO API version!\n");
412                         close(vfio_container_fd);
413                         return -1;
414                 }
415
416                 ret = vfio_has_supported_extensions(vfio_container_fd);
417                 if (ret) {
418                         RTE_LOG(ERR, EAL, "  no supported IOMMU "
419                                         "extensions found!\n");
420                         return -1;
421                 }
422
423                 return vfio_container_fd;
424         } else {
425                 /*
426                  * if we're in a secondary process, request container fd from the
427                  * primary process via our socket
428                  */
429                 int socket_fd;
430
431                 socket_fd = vfio_mp_sync_connect_to_primary();
432                 if (socket_fd < 0) {
433                         RTE_LOG(ERR, EAL, "  cannot connect to primary process!\n");
434                         return -1;
435                 }
436                 if (vfio_mp_sync_send_request(socket_fd, SOCKET_REQ_CONTAINER) < 0) {
437                         RTE_LOG(ERR, EAL, "  cannot request container fd!\n");
438                         close(socket_fd);
439                         return -1;
440                 }
441                 vfio_container_fd = vfio_mp_sync_receive_fd(socket_fd);
442                 if (vfio_container_fd < 0) {
443                         RTE_LOG(ERR, EAL, "  cannot get container fd!\n");
444                         close(socket_fd);
445                         return -1;
446                 }
447                 close(socket_fd);
448                 return vfio_container_fd;
449         }
450
451         return -1;
452 }
453
454 int
455 vfio_get_group_no(const char *sysfs_base,
456                 const char *dev_addr, int *iommu_group_no)
457 {
458         char linkname[PATH_MAX];
459         char filename[PATH_MAX];
460         char *tok[16], *group_tok, *end;
461         int ret;
462
463         memset(linkname, 0, sizeof(linkname));
464         memset(filename, 0, sizeof(filename));
465
466         /* try to find out IOMMU group for this device */
467         snprintf(linkname, sizeof(linkname),
468                          "%s/%s/iommu_group", sysfs_base, dev_addr);
469
470         ret = readlink(linkname, filename, sizeof(filename));
471
472         /* if the link doesn't exist, no VFIO for us */
473         if (ret < 0)
474                 return 0;
475
476         ret = rte_strsplit(filename, sizeof(filename),
477                         tok, RTE_DIM(tok), '/');
478
479         if (ret <= 0) {
480                 RTE_LOG(ERR, EAL, "  %s cannot get IOMMU group\n", dev_addr);
481                 return -1;
482         }
483
484         /* IOMMU group is always the last token */
485         errno = 0;
486         group_tok = tok[ret - 1];
487         end = group_tok;
488         *iommu_group_no = strtol(group_tok, &end, 10);
489         if ((end != group_tok && *end != '\0') || errno != 0) {
490                 RTE_LOG(ERR, EAL, "  %s error parsing IOMMU number!\n", dev_addr);
491                 return -1;
492         }
493
494         return 1;
495 }
496
497 int
498 vfio_type1_dma_map(int vfio_container_fd)
499 {
500         const struct rte_memseg *ms = rte_eal_get_physmem_layout();
501         int i, ret;
502
503         /* map all DPDK segments for DMA. use 1:1 PA to IOVA mapping */
504         for (i = 0; i < RTE_MAX_MEMSEG; i++) {
505                 struct vfio_iommu_type1_dma_map dma_map;
506
507                 if (ms[i].addr == NULL)
508                         break;
509
510                 memset(&dma_map, 0, sizeof(dma_map));
511                 dma_map.argsz = sizeof(struct vfio_iommu_type1_dma_map);
512                 dma_map.vaddr = ms[i].addr_64;
513                 dma_map.size = ms[i].len;
514                 dma_map.iova = ms[i].phys_addr;
515                 dma_map.flags = VFIO_DMA_MAP_FLAG_READ | VFIO_DMA_MAP_FLAG_WRITE;
516
517                 ret = ioctl(vfio_container_fd, VFIO_IOMMU_MAP_DMA, &dma_map);
518
519                 if (ret) {
520                         RTE_LOG(ERR, EAL, "  cannot set up DMA remapping, "
521                                         "error %i (%s)\n", errno, strerror(errno));
522                         return -1;
523                 }
524         }
525
526         return 0;
527 }
528
529 int
530 vfio_noiommu_dma_map(int __rte_unused vfio_container_fd)
531 {
532         /* No-IOMMU mode does not need DMA mapping */
533         return 0;
534 }
535
536 #endif