Re: [lng-odp] [PATCH CATERPILLAR v3] linux-gen: mediated devices common code
Mykyta Iziumtsev(MykytaI) replied on github web page: platform/linux-generic/pktio/mdev.c @@ -0,0 +1,589 @@ +/* Copyright (c) 2018, Linaro Limited + * All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include "config.h" + +#ifdef ODP_MDEV + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#include +#include +#include + +#include + +#include +#include + +/** + * returns a valid VFIO container + * fd must be closed by caller + */ +static int get_container(void) +{ + int container; + int ret; + + /* Create a new container */ + container = open("/dev/vfio/vfio", O_RDWR); + if (container < 0) { + ODP_ERR("Failed to create new VFIO container\n"); + goto out; + } + + ret = ioctl(container, VFIO_GET_API_VERSION); + if (ret != VFIO_API_VERSION) { + ODP_ERR("VFIO API version mismatch: expected %i, got %i\n", + VFIO_API_VERSION, ret); + goto out; + } + + ret = ioctl(container, VFIO_CHECK_EXTENSION, VFIO_TYPE1_IOMMU); + if (!ret) { + ODP_ERR("Container doesn't support VFIO_TYPE1_IOMMU\n"); + goto out; + } + + return container; + +out: + if (container != -1) + close(container); + return -1; +} + +/** + * returns a valid VFIO group + * fd must be closed by caller + */ +static int get_group(int grp_id) +{ + char path[32]; + int group; + int ret; + struct vfio_group_status group_status = { + .argsz = sizeof(group_status) + }; + + snprintf(path, sizeof(path), "/dev/vfio/%d", grp_id); + group = open(path, O_RDWR); + if (group < 0) { + ODP_ERR("Failed to open %s: %s\n", path, strerror(errno)); + goto out; + } + + ret = ioctl(group, VFIO_GROUP_GET_STATUS, _status); + if (ret < 0) { + ODP_ERR("Failed to get group status\n"); + goto out; + } + + /* Test the group is viable and available */ + if (!(group_status.flags & VFIO_GROUP_FLAGS_VIABLE)) { + ODP_ERR("Group is not viable\n"); + goto out; + } + + return group; + +out: + if (group != -1) + close(group); + return -1; +} + +static void vfio_find_sparse_mmaps(struct vfio_info_cap_header *hdr, + struct vfio_region_info_cap_sparse_mmap + **sparse) +{ + *sparse = + odp_container_of(hdr, struct vfio_region_info_cap_sparse_mmap, +header); +} + +static struct vfio_info_cap_header * +vfio_get_region_info_cap(struct vfio_region_info *info, __u16 id) +{ + struct vfio_info_cap_header *hdr; + void *ptr = info; + + if (!(info->flags & VFIO_REGION_INFO_FLAG_CAPS)) + return NULL; + + for (hdr = +(struct vfio_info_cap_header *)((char *)ptr + info->cap_offset); +hdr != ptr; +hdr = (struct vfio_info_cap_header *)((char *)ptr + hdr->next)) { Comment: I've fixed clang compilation. I guess if we insert compilation test into .travis.yml without proper Ubuntu 17.10 docker images -- it will fail on every upcoming PR which doesn't make much sense. I believe it shall be in separate PR accompanied with all prerequisite changes in Travis images. What do you think ? > Mykyta Iziumtsev(MykytaI) wrote: > Thanks, updated code according to an assumption that we have just one file in > the directory which is UUID we're looking for. >> Bill Fischofer(Bill-Fischofer-Linaro) wrote: >> Either would be good. This can always be enhanced in follow-on PRs, but each >> PR should stand alone. >>> Bill Fischofer(Bill-Fischofer-Linaro) wrote: >>> OK Bill Fischofer(Bill-Fischofer-Linaro) wrote: OK. > Bill Fischofer(Bill-Fischofer-Linaro) wrote: > Specifying `./configure --enable-mdev-support=yes CC=clang` results in > lines 130 and 132 being flagged by clang: > ``` > CC pktio/mdev.lo > pktio/mdev.c:130:7: error: cast from 'char *' to 'struct > vfio_info_cap_header *' > increases required alignment from 1 to 4 [-Werror,-Wcast-align] > (struct vfio_info_cap_header *)((char *)ptr + > info->cap_offset); > > ^~~ > pktio/mdev.c:132:13: error: cast from 'char *' to > 'struct vfio_info_cap_header *' increases required alignment from 1 > to 4 > [-Werror,-Wcast-align] > hdr = (struct vfio_info_cap_header *)((char *)ptr + > hdr->next)) { > > ^~~~ > 2 errors generated. > Makefile:1222: recipe for
Re: [lng-odp] [PATCH CATERPILLAR v3] linux-gen: mediated devices common code
Mykyta Iziumtsev(MykytaI) replied on github web page: platform/linux-generic/pktio/mdev.c @@ -0,0 +1,585 @@ +/* Copyright (c) 2018, Linaro Limited + * All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include "config.h" + +#ifdef ODP_MDEV + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + +#include +#include + +#include +#include + +/** + * returns a valid VFIO container + * fd must be closed by caller + */ +static int get_container(void) +{ + int ret; + int container; + /* Create a new container */ + container = open("/dev/vfio/vfio", O_RDWR); + + if (container < 0) + return container; + + ret = ioctl(container, VFIO_GET_API_VERSION); + if (ret != VFIO_API_VERSION) { + ODP_ERR("Unknown API version\n"); + goto out; + } + + if (!ioctl(container, VFIO_CHECK_EXTENSION, VFIO_TYPE1_IOMMU)) { + ODP_ERR("Doesn't support the IOMMU driver we want\n"); + goto out; + } + + return container; +out: + close(container); + container = -1; + return ret; +} + +/** + * returns a valid VFIO group + * fd must be close by caller + */ +static int get_group(int grp_id) +{ + char path[64]; + int ret; + int group; + struct vfio_group_status group_status = { + .argsz = sizeof(group_status) + }; + + snprintf(path, sizeof(path), "/dev/vfio/%d", grp_id); + group = open(path, O_RDWR); + if (group < 0) { + ODP_ERR("Failed to open %s, %d (%s)\n", + path, group, strerror(errno)); + return group; + } + + ret = ioctl(group, VFIO_GROUP_GET_STATUS, _status); + + if (ret < 0) { + ODP_ERR("ioctl(VFIO_GROUP_GET_STATUS) failed\n"); + goto out; + } + + /* Test the group is viable and available */ + if (!(group_status.flags & VFIO_GROUP_FLAGS_VIABLE)) { + ODP_ERR("Group is not viable\n"); + goto out; + } + + return group; +out: + close(group); + group = -1; + return ret; +} + +static void vfio_find_sparse_mmaps(struct vfio_info_cap_header *hdr, + struct vfio_region_info_cap_sparse_mmap + **sparse) +{ + *sparse = + odp_container_of(hdr, struct vfio_region_info_cap_sparse_mmap, +header); +} + +static struct vfio_info_cap_header * +vfio_get_region_info_cap(struct vfio_region_info *info, __u16 id) +{ + struct vfio_info_cap_header *hdr; + void *ptr = info; + + if (!(info->flags & VFIO_REGION_INFO_FLAG_CAPS)) + return NULL; + + for (hdr = +(struct vfio_info_cap_header *)((char *)ptr + info->cap_offset); +hdr != ptr; +hdr = (struct vfio_info_cap_header *)((char *)ptr + hdr->next)) { + if (hdr->id == id) + return hdr; + } + + return NULL; +} + +static struct vfio_info_cap_header * +vfio_get_cap_info(struct vfio_region_info *region_info, __u16 id) +{ + struct vfio_info_cap_header *caps = NULL; + + caps = vfio_get_region_info_cap(region_info, id); + + return caps; +} + +int vfio_get_region_sparse_mmaps(struct vfio_region_info *region_info, +struct vfio_region_info_cap_sparse_mmap +**sparse) +{ + struct vfio_info_cap_header *caps = NULL; + int ret = -ENOENT; + + if (region_info->flags & VFIO_REGION_INFO_FLAG_CAPS && + region_info->argsz > sizeof(*region_info)) { + caps = vfio_get_cap_info(region_info, +VFIO_REGION_INFO_CAP_SPARSE_MMAP); + if (!caps) + goto out; + vfio_find_sparse_mmaps(caps, sparse); + if (*sparse) { + for (uint32_t i = 0; i < (*sparse)->nr_areas; i++) + ODP_DBG("Sparse region: %d 0x%llx %llu\n", i, + (*sparse)->areas[i].offset, + (*sparse)->areas[i].size); + } + + ret = 0; + } + +out: + return ret; +} + +/** Match capability type + * returns 0 on succcess + */ +int vfio_get_region_cap_type(struct vfio_region_info *region_info, +mdev_region_class_t *class_info) +{ + struct vfio_info_cap_header *caps = NULL; + int ret = 0; + struct vfio_region_info_cap_type *cap_type; + + if (region_info->flags & VFIO_REGION_INFO_FLAG_CAPS && + region_info->argsz > sizeof(*region_info)) { + caps = vfio_get_cap_info(region_info, +