Skip to content
Permalink
Browse files
iommufd: Add a selftest
Cover the essential functionality of the iommufd with a simple test.

Signed-off-by: Jason Gunthorpe <jgg@nvidia.com>
Signed-off-by: Nicolin Chen <nicolinc@nvidia.com>
Signed-off-by: Liu Yi L <yi.l.liu@intel.com>
  • Loading branch information
jgunthorpe authored and yiliu1765 committed Feb 15, 2022
1 parent 1be8c65 commit 047031aaa50c5daed9c24fa0701f7016d4ff6934
Show file tree
Hide file tree
Showing 12 changed files with 1,873 additions and 0 deletions.
@@ -10,3 +10,11 @@ config IOMMUFD
to userspace drivers.

If you don't know what to do here, say N.

config IOMMUFD_TEST
bool "IOMMU Userspace API Test support"
depends on IOMMUFD
default n
help
This is dangerous, do not enable unless running
tools/testing/selftests/iommu
@@ -8,4 +8,6 @@ iommufd-y := \
pages.o \
vfio_compat.o

iommufd-$(CONFIG_IOMMUFD_TEST) += selftest.o

obj-$(CONFIG_IOMMUFD) += iommufd.o
@@ -98,6 +98,9 @@ enum iommufd_object_type {
IOMMUFD_OBJ_NONE,
IOMMUFD_OBJ_ANY = IOMMUFD_OBJ_NONE,
IOMMUFD_OBJ_DEVICE,
#ifdef CONFIG_IOMMUFD_TEST
IOMMUFD_OBJ_SELFTEST,
#endif
IOMMUFD_OBJ_HW_PAGETABLE,
IOMMUFD_OBJ_IOAS_PAGETABLE,
IOMMUFD_OBJ_MAX,
@@ -207,4 +210,10 @@ void iommufd_hw_pagetable_destroy(struct iommufd_object *obj);

void iommufd_device_destroy(struct iommufd_object *obj);

#ifdef CONFIG_IOMMUFD_TEST
int iommufd_test(struct iommufd_ucmd *ucmd);
void iommufd_selftest_destroy(struct iommufd_object *obj);
extern size_t iommufd_test_memory_limit;
#endif

#endif
@@ -0,0 +1,65 @@
// SPDX-License-Identifier: GPL-2.0
/* Copyright (c) 2021, NVIDIA CORPORATION & AFFILIATES.
*/
#ifndef _UAPI_IOMMUFD_TEST_H
#define _UAPI_IOMMUFD_TEST_H

#include <linux/types.h>
#include <linux/iommufd.h>

enum {
IOMMU_TEST_OP_ADD_RESERVED,
IOMMU_TEST_OP_MOCK_DOMAIN,
IOMMU_TEST_OP_MD_CHECK_MAP,
IOMMU_TEST_OP_MD_CHECK_REFS,
IOMMU_TEST_OP_ACCESS_PAGES,
IOMMU_TEST_OP_SET_TEMP_MEMORY_LIMIT,
};

enum {
MOCK_APERTURE_START = 1UL << 24,
MOCK_APERTURE_LAST = (1UL << 31) - 1,
};

enum {
MOCK_FLAGS_ACCESS_WRITE = 1 << 0,
};

struct iommu_test_cmd {
__u32 size;
__u32 op;
__u32 id;
union {
struct {
__u32 device_id;
} mock_domain;
struct {
__aligned_u64 start;
__aligned_u64 length;
} add_reserved;
struct {
__aligned_u64 iova;
__aligned_u64 length;
__aligned_u64 uptr;
} check_map;
struct {
__aligned_u64 length;
__aligned_u64 uptr;
__u32 refs;
} check_refs;
struct {
__u32 flags;
__u32 out_access_id;
__aligned_u64 iova;
__aligned_u64 length;
__aligned_u64 uptr;
} access_pages;
struct {
__u32 limit;
} memory_limit;
};
__u32 last;
};
#define IOMMU_TEST_CMD _IO(IOMMUFD_TYPE, IOMMUFD_CMD_BASE + 32)

#endif
@@ -24,6 +24,7 @@
#include <uapi/linux/iommufd.h>

#include "iommufd_private.h"
#include "iommufd_test.h"

struct iommufd_object_ops {
void (*destroy)(struct iommufd_object *obj);
@@ -187,6 +188,9 @@ union ucmd_buffer {
struct iommu_ioas_pagetable_map map;
struct iommu_ioas_pagetable_unmap unmap;
struct iommu_destroy destroy;
#ifdef CONFIG_IOMMUFD_TEST
struct iommu_test_cmd test;
#endif
};

struct iommufd_ioctl_op {
@@ -220,6 +224,9 @@ static struct iommufd_ioctl_op iommufd_ioctl_ops[] = {
struct iommu_ioas_pagetable_unmap, length),
IOCTL_OP(IOMMU_VFIO_IOAS, iommufd_vfio_ioas, struct iommu_vfio_ioas,
reserved),
#ifdef CONFIG_IOMMUFD_TEST
IOCTL_OP(IOMMU_TEST_CMD, iommufd_test, struct iommu_test_cmd, last),
#endif
};

static long iommufd_fops_ioctl(struct file *filp, unsigned int cmd,
@@ -296,6 +303,11 @@ static struct iommufd_object_ops iommufd_object_ops[] = {
[IOMMUFD_OBJ_HW_PAGETABLE] = {
.destroy = iommufd_hw_pagetable_destroy,
},
#ifdef CONFIG_IOMMUFD_TEST
[IOMMUFD_OBJ_SELFTEST] = {
.destroy = iommufd_selftest_destroy,
},
#endif
};

static struct miscdevice iommu_misc_dev = {
@@ -48,7 +48,11 @@

#include "io_pagetable.h"

#ifndef CONFIG_IOMMUFD_TEST
#define TEMP_MEMORY_LIMIT 65536
#else
#define TEMP_MEMORY_LIMIT iommufd_test_memory_limit
#endif
#define BATCH_BACKUP_SIZE 32

/*

0 comments on commit 047031a

Please sign in to comment.