162306a36Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0-only */ 262306a36Sopenharmony_ci/* Copyright (c) 2021-2022, NVIDIA CORPORATION & AFFILIATES 362306a36Sopenharmony_ci */ 462306a36Sopenharmony_ci#ifndef __IOMMUFD_PRIVATE_H 562306a36Sopenharmony_ci#define __IOMMUFD_PRIVATE_H 662306a36Sopenharmony_ci 762306a36Sopenharmony_ci#include <linux/rwsem.h> 862306a36Sopenharmony_ci#include <linux/xarray.h> 962306a36Sopenharmony_ci#include <linux/refcount.h> 1062306a36Sopenharmony_ci#include <linux/uaccess.h> 1162306a36Sopenharmony_ci 1262306a36Sopenharmony_cistruct iommu_domain; 1362306a36Sopenharmony_cistruct iommu_group; 1462306a36Sopenharmony_cistruct iommu_option; 1562306a36Sopenharmony_cistruct iommufd_device; 1662306a36Sopenharmony_ci 1762306a36Sopenharmony_cistruct iommufd_ctx { 1862306a36Sopenharmony_ci struct file *file; 1962306a36Sopenharmony_ci struct xarray objects; 2062306a36Sopenharmony_ci struct xarray groups; 2162306a36Sopenharmony_ci 2262306a36Sopenharmony_ci u8 account_mode; 2362306a36Sopenharmony_ci /* Compatibility with VFIO no iommu */ 2462306a36Sopenharmony_ci u8 no_iommu_mode; 2562306a36Sopenharmony_ci struct iommufd_ioas *vfio_ioas; 2662306a36Sopenharmony_ci}; 2762306a36Sopenharmony_ci 2862306a36Sopenharmony_ci/* 2962306a36Sopenharmony_ci * The IOVA to PFN map. The map automatically copies the PFNs into multiple 3062306a36Sopenharmony_ci * domains and permits sharing of PFNs between io_pagetable instances. This 3162306a36Sopenharmony_ci * supports both a design where IOAS's are 1:1 with a domain (eg because the 3262306a36Sopenharmony_ci * domain is HW customized), or where the IOAS is 1:N with multiple generic 3362306a36Sopenharmony_ci * domains. The io_pagetable holds an interval tree of iopt_areas which point 3462306a36Sopenharmony_ci * to shared iopt_pages which hold the pfns mapped to the page table. 3562306a36Sopenharmony_ci * 3662306a36Sopenharmony_ci * The locking order is domains_rwsem -> iova_rwsem -> pages::mutex 3762306a36Sopenharmony_ci */ 3862306a36Sopenharmony_cistruct io_pagetable { 3962306a36Sopenharmony_ci struct rw_semaphore domains_rwsem; 4062306a36Sopenharmony_ci struct xarray domains; 4162306a36Sopenharmony_ci struct xarray access_list; 4262306a36Sopenharmony_ci unsigned int next_domain_id; 4362306a36Sopenharmony_ci 4462306a36Sopenharmony_ci struct rw_semaphore iova_rwsem; 4562306a36Sopenharmony_ci struct rb_root_cached area_itree; 4662306a36Sopenharmony_ci /* IOVA that cannot become reserved, struct iopt_allowed */ 4762306a36Sopenharmony_ci struct rb_root_cached allowed_itree; 4862306a36Sopenharmony_ci /* IOVA that cannot be allocated, struct iopt_reserved */ 4962306a36Sopenharmony_ci struct rb_root_cached reserved_itree; 5062306a36Sopenharmony_ci u8 disable_large_pages; 5162306a36Sopenharmony_ci unsigned long iova_alignment; 5262306a36Sopenharmony_ci}; 5362306a36Sopenharmony_ci 5462306a36Sopenharmony_civoid iopt_init_table(struct io_pagetable *iopt); 5562306a36Sopenharmony_civoid iopt_destroy_table(struct io_pagetable *iopt); 5662306a36Sopenharmony_ciint iopt_get_pages(struct io_pagetable *iopt, unsigned long iova, 5762306a36Sopenharmony_ci unsigned long length, struct list_head *pages_list); 5862306a36Sopenharmony_civoid iopt_free_pages_list(struct list_head *pages_list); 5962306a36Sopenharmony_cienum { 6062306a36Sopenharmony_ci IOPT_ALLOC_IOVA = 1 << 0, 6162306a36Sopenharmony_ci}; 6262306a36Sopenharmony_ciint iopt_map_user_pages(struct iommufd_ctx *ictx, struct io_pagetable *iopt, 6362306a36Sopenharmony_ci unsigned long *iova, void __user *uptr, 6462306a36Sopenharmony_ci unsigned long length, int iommu_prot, 6562306a36Sopenharmony_ci unsigned int flags); 6662306a36Sopenharmony_ciint iopt_map_pages(struct io_pagetable *iopt, struct list_head *pages_list, 6762306a36Sopenharmony_ci unsigned long length, unsigned long *dst_iova, 6862306a36Sopenharmony_ci int iommu_prot, unsigned int flags); 6962306a36Sopenharmony_ciint iopt_unmap_iova(struct io_pagetable *iopt, unsigned long iova, 7062306a36Sopenharmony_ci unsigned long length, unsigned long *unmapped); 7162306a36Sopenharmony_ciint iopt_unmap_all(struct io_pagetable *iopt, unsigned long *unmapped); 7262306a36Sopenharmony_ci 7362306a36Sopenharmony_civoid iommufd_access_notify_unmap(struct io_pagetable *iopt, unsigned long iova, 7462306a36Sopenharmony_ci unsigned long length); 7562306a36Sopenharmony_ciint iopt_table_add_domain(struct io_pagetable *iopt, 7662306a36Sopenharmony_ci struct iommu_domain *domain); 7762306a36Sopenharmony_civoid iopt_table_remove_domain(struct io_pagetable *iopt, 7862306a36Sopenharmony_ci struct iommu_domain *domain); 7962306a36Sopenharmony_ciint iopt_table_enforce_dev_resv_regions(struct io_pagetable *iopt, 8062306a36Sopenharmony_ci struct device *dev, 8162306a36Sopenharmony_ci phys_addr_t *sw_msi_start); 8262306a36Sopenharmony_ciint iopt_set_allow_iova(struct io_pagetable *iopt, 8362306a36Sopenharmony_ci struct rb_root_cached *allowed_iova); 8462306a36Sopenharmony_ciint iopt_reserve_iova(struct io_pagetable *iopt, unsigned long start, 8562306a36Sopenharmony_ci unsigned long last, void *owner); 8662306a36Sopenharmony_civoid iopt_remove_reserved_iova(struct io_pagetable *iopt, void *owner); 8762306a36Sopenharmony_ciint iopt_cut_iova(struct io_pagetable *iopt, unsigned long *iovas, 8862306a36Sopenharmony_ci size_t num_iovas); 8962306a36Sopenharmony_civoid iopt_enable_large_pages(struct io_pagetable *iopt); 9062306a36Sopenharmony_ciint iopt_disable_large_pages(struct io_pagetable *iopt); 9162306a36Sopenharmony_ci 9262306a36Sopenharmony_cistruct iommufd_ucmd { 9362306a36Sopenharmony_ci struct iommufd_ctx *ictx; 9462306a36Sopenharmony_ci void __user *ubuffer; 9562306a36Sopenharmony_ci u32 user_size; 9662306a36Sopenharmony_ci void *cmd; 9762306a36Sopenharmony_ci}; 9862306a36Sopenharmony_ci 9962306a36Sopenharmony_ciint iommufd_vfio_ioctl(struct iommufd_ctx *ictx, unsigned int cmd, 10062306a36Sopenharmony_ci unsigned long arg); 10162306a36Sopenharmony_ci 10262306a36Sopenharmony_ci/* Copy the response in ucmd->cmd back to userspace. */ 10362306a36Sopenharmony_cistatic inline int iommufd_ucmd_respond(struct iommufd_ucmd *ucmd, 10462306a36Sopenharmony_ci size_t cmd_len) 10562306a36Sopenharmony_ci{ 10662306a36Sopenharmony_ci if (copy_to_user(ucmd->ubuffer, ucmd->cmd, 10762306a36Sopenharmony_ci min_t(size_t, ucmd->user_size, cmd_len))) 10862306a36Sopenharmony_ci return -EFAULT; 10962306a36Sopenharmony_ci return 0; 11062306a36Sopenharmony_ci} 11162306a36Sopenharmony_ci 11262306a36Sopenharmony_cienum iommufd_object_type { 11362306a36Sopenharmony_ci IOMMUFD_OBJ_NONE, 11462306a36Sopenharmony_ci IOMMUFD_OBJ_ANY = IOMMUFD_OBJ_NONE, 11562306a36Sopenharmony_ci IOMMUFD_OBJ_DEVICE, 11662306a36Sopenharmony_ci IOMMUFD_OBJ_HW_PAGETABLE, 11762306a36Sopenharmony_ci IOMMUFD_OBJ_IOAS, 11862306a36Sopenharmony_ci IOMMUFD_OBJ_ACCESS, 11962306a36Sopenharmony_ci#ifdef CONFIG_IOMMUFD_TEST 12062306a36Sopenharmony_ci IOMMUFD_OBJ_SELFTEST, 12162306a36Sopenharmony_ci#endif 12262306a36Sopenharmony_ci IOMMUFD_OBJ_MAX, 12362306a36Sopenharmony_ci}; 12462306a36Sopenharmony_ci 12562306a36Sopenharmony_ci/* Base struct for all objects with a userspace ID handle. */ 12662306a36Sopenharmony_cistruct iommufd_object { 12762306a36Sopenharmony_ci struct rw_semaphore destroy_rwsem; 12862306a36Sopenharmony_ci refcount_t users; 12962306a36Sopenharmony_ci enum iommufd_object_type type; 13062306a36Sopenharmony_ci unsigned int id; 13162306a36Sopenharmony_ci}; 13262306a36Sopenharmony_ci 13362306a36Sopenharmony_cistatic inline bool iommufd_lock_obj(struct iommufd_object *obj) 13462306a36Sopenharmony_ci{ 13562306a36Sopenharmony_ci if (!down_read_trylock(&obj->destroy_rwsem)) 13662306a36Sopenharmony_ci return false; 13762306a36Sopenharmony_ci if (!refcount_inc_not_zero(&obj->users)) { 13862306a36Sopenharmony_ci up_read(&obj->destroy_rwsem); 13962306a36Sopenharmony_ci return false; 14062306a36Sopenharmony_ci } 14162306a36Sopenharmony_ci return true; 14262306a36Sopenharmony_ci} 14362306a36Sopenharmony_ci 14462306a36Sopenharmony_cistruct iommufd_object *iommufd_get_object(struct iommufd_ctx *ictx, u32 id, 14562306a36Sopenharmony_ci enum iommufd_object_type type); 14662306a36Sopenharmony_cistatic inline void iommufd_put_object(struct iommufd_object *obj) 14762306a36Sopenharmony_ci{ 14862306a36Sopenharmony_ci refcount_dec(&obj->users); 14962306a36Sopenharmony_ci up_read(&obj->destroy_rwsem); 15062306a36Sopenharmony_ci} 15162306a36Sopenharmony_ci 15262306a36Sopenharmony_civoid iommufd_object_abort(struct iommufd_ctx *ictx, struct iommufd_object *obj); 15362306a36Sopenharmony_civoid iommufd_object_abort_and_destroy(struct iommufd_ctx *ictx, 15462306a36Sopenharmony_ci struct iommufd_object *obj); 15562306a36Sopenharmony_civoid iommufd_object_finalize(struct iommufd_ctx *ictx, 15662306a36Sopenharmony_ci struct iommufd_object *obj); 15762306a36Sopenharmony_civoid __iommufd_object_destroy_user(struct iommufd_ctx *ictx, 15862306a36Sopenharmony_ci struct iommufd_object *obj, bool allow_fail); 15962306a36Sopenharmony_cistatic inline void iommufd_object_destroy_user(struct iommufd_ctx *ictx, 16062306a36Sopenharmony_ci struct iommufd_object *obj) 16162306a36Sopenharmony_ci{ 16262306a36Sopenharmony_ci __iommufd_object_destroy_user(ictx, obj, false); 16362306a36Sopenharmony_ci} 16462306a36Sopenharmony_cistatic inline void iommufd_object_deref_user(struct iommufd_ctx *ictx, 16562306a36Sopenharmony_ci struct iommufd_object *obj) 16662306a36Sopenharmony_ci{ 16762306a36Sopenharmony_ci __iommufd_object_destroy_user(ictx, obj, true); 16862306a36Sopenharmony_ci} 16962306a36Sopenharmony_ci 17062306a36Sopenharmony_cistruct iommufd_object *_iommufd_object_alloc(struct iommufd_ctx *ictx, 17162306a36Sopenharmony_ci size_t size, 17262306a36Sopenharmony_ci enum iommufd_object_type type); 17362306a36Sopenharmony_ci 17462306a36Sopenharmony_ci#define iommufd_object_alloc(ictx, ptr, type) \ 17562306a36Sopenharmony_ci container_of(_iommufd_object_alloc( \ 17662306a36Sopenharmony_ci ictx, \ 17762306a36Sopenharmony_ci sizeof(*(ptr)) + BUILD_BUG_ON_ZERO( \ 17862306a36Sopenharmony_ci offsetof(typeof(*(ptr)), \ 17962306a36Sopenharmony_ci obj) != 0), \ 18062306a36Sopenharmony_ci type), \ 18162306a36Sopenharmony_ci typeof(*(ptr)), obj) 18262306a36Sopenharmony_ci 18362306a36Sopenharmony_ci/* 18462306a36Sopenharmony_ci * The IO Address Space (IOAS) pagetable is a virtual page table backed by the 18562306a36Sopenharmony_ci * io_pagetable object. It is a user controlled mapping of IOVA -> PFNs. The 18662306a36Sopenharmony_ci * mapping is copied into all of the associated domains and made available to 18762306a36Sopenharmony_ci * in-kernel users. 18862306a36Sopenharmony_ci * 18962306a36Sopenharmony_ci * Every iommu_domain that is created is wrapped in a iommufd_hw_pagetable 19062306a36Sopenharmony_ci * object. When we go to attach a device to an IOAS we need to get an 19162306a36Sopenharmony_ci * iommu_domain and wrapping iommufd_hw_pagetable for it. 19262306a36Sopenharmony_ci * 19362306a36Sopenharmony_ci * An iommu_domain & iommfd_hw_pagetable will be automatically selected 19462306a36Sopenharmony_ci * for a device based on the hwpt_list. If no suitable iommu_domain 19562306a36Sopenharmony_ci * is found a new iommu_domain will be created. 19662306a36Sopenharmony_ci */ 19762306a36Sopenharmony_cistruct iommufd_ioas { 19862306a36Sopenharmony_ci struct iommufd_object obj; 19962306a36Sopenharmony_ci struct io_pagetable iopt; 20062306a36Sopenharmony_ci struct mutex mutex; 20162306a36Sopenharmony_ci struct list_head hwpt_list; 20262306a36Sopenharmony_ci}; 20362306a36Sopenharmony_ci 20462306a36Sopenharmony_cistatic inline struct iommufd_ioas *iommufd_get_ioas(struct iommufd_ctx *ictx, 20562306a36Sopenharmony_ci u32 id) 20662306a36Sopenharmony_ci{ 20762306a36Sopenharmony_ci return container_of(iommufd_get_object(ictx, id, 20862306a36Sopenharmony_ci IOMMUFD_OBJ_IOAS), 20962306a36Sopenharmony_ci struct iommufd_ioas, obj); 21062306a36Sopenharmony_ci} 21162306a36Sopenharmony_ci 21262306a36Sopenharmony_cistruct iommufd_ioas *iommufd_ioas_alloc(struct iommufd_ctx *ictx); 21362306a36Sopenharmony_ciint iommufd_ioas_alloc_ioctl(struct iommufd_ucmd *ucmd); 21462306a36Sopenharmony_civoid iommufd_ioas_destroy(struct iommufd_object *obj); 21562306a36Sopenharmony_ciint iommufd_ioas_iova_ranges(struct iommufd_ucmd *ucmd); 21662306a36Sopenharmony_ciint iommufd_ioas_allow_iovas(struct iommufd_ucmd *ucmd); 21762306a36Sopenharmony_ciint iommufd_ioas_map(struct iommufd_ucmd *ucmd); 21862306a36Sopenharmony_ciint iommufd_ioas_copy(struct iommufd_ucmd *ucmd); 21962306a36Sopenharmony_ciint iommufd_ioas_unmap(struct iommufd_ucmd *ucmd); 22062306a36Sopenharmony_ciint iommufd_ioas_option(struct iommufd_ucmd *ucmd); 22162306a36Sopenharmony_ciint iommufd_option_rlimit_mode(struct iommu_option *cmd, 22262306a36Sopenharmony_ci struct iommufd_ctx *ictx); 22362306a36Sopenharmony_ci 22462306a36Sopenharmony_ciint iommufd_vfio_ioas(struct iommufd_ucmd *ucmd); 22562306a36Sopenharmony_ci 22662306a36Sopenharmony_ci/* 22762306a36Sopenharmony_ci * A HW pagetable is called an iommu_domain inside the kernel. This user object 22862306a36Sopenharmony_ci * allows directly creating and inspecting the domains. Domains that have kernel 22962306a36Sopenharmony_ci * owned page tables will be associated with an iommufd_ioas that provides the 23062306a36Sopenharmony_ci * IOVA to PFN map. 23162306a36Sopenharmony_ci */ 23262306a36Sopenharmony_cistruct iommufd_hw_pagetable { 23362306a36Sopenharmony_ci struct iommufd_object obj; 23462306a36Sopenharmony_ci struct iommufd_ioas *ioas; 23562306a36Sopenharmony_ci struct iommu_domain *domain; 23662306a36Sopenharmony_ci bool auto_domain : 1; 23762306a36Sopenharmony_ci bool enforce_cache_coherency : 1; 23862306a36Sopenharmony_ci bool msi_cookie : 1; 23962306a36Sopenharmony_ci /* Head at iommufd_ioas::hwpt_list */ 24062306a36Sopenharmony_ci struct list_head hwpt_item; 24162306a36Sopenharmony_ci}; 24262306a36Sopenharmony_ci 24362306a36Sopenharmony_cistruct iommufd_hw_pagetable * 24462306a36Sopenharmony_ciiommufd_hw_pagetable_alloc(struct iommufd_ctx *ictx, struct iommufd_ioas *ioas, 24562306a36Sopenharmony_ci struct iommufd_device *idev, bool immediate_attach); 24662306a36Sopenharmony_ciint iommufd_hw_pagetable_enforce_cc(struct iommufd_hw_pagetable *hwpt); 24762306a36Sopenharmony_ciint iommufd_hw_pagetable_attach(struct iommufd_hw_pagetable *hwpt, 24862306a36Sopenharmony_ci struct iommufd_device *idev); 24962306a36Sopenharmony_cistruct iommufd_hw_pagetable * 25062306a36Sopenharmony_ciiommufd_hw_pagetable_detach(struct iommufd_device *idev); 25162306a36Sopenharmony_civoid iommufd_hw_pagetable_destroy(struct iommufd_object *obj); 25262306a36Sopenharmony_civoid iommufd_hw_pagetable_abort(struct iommufd_object *obj); 25362306a36Sopenharmony_ciint iommufd_hwpt_alloc(struct iommufd_ucmd *ucmd); 25462306a36Sopenharmony_ci 25562306a36Sopenharmony_cistatic inline void iommufd_hw_pagetable_put(struct iommufd_ctx *ictx, 25662306a36Sopenharmony_ci struct iommufd_hw_pagetable *hwpt) 25762306a36Sopenharmony_ci{ 25862306a36Sopenharmony_ci lockdep_assert_not_held(&hwpt->ioas->mutex); 25962306a36Sopenharmony_ci if (hwpt->auto_domain) 26062306a36Sopenharmony_ci iommufd_object_deref_user(ictx, &hwpt->obj); 26162306a36Sopenharmony_ci else 26262306a36Sopenharmony_ci refcount_dec(&hwpt->obj.users); 26362306a36Sopenharmony_ci} 26462306a36Sopenharmony_ci 26562306a36Sopenharmony_cistruct iommufd_group { 26662306a36Sopenharmony_ci struct kref ref; 26762306a36Sopenharmony_ci struct mutex lock; 26862306a36Sopenharmony_ci struct iommufd_ctx *ictx; 26962306a36Sopenharmony_ci struct iommu_group *group; 27062306a36Sopenharmony_ci struct iommufd_hw_pagetable *hwpt; 27162306a36Sopenharmony_ci struct list_head device_list; 27262306a36Sopenharmony_ci phys_addr_t sw_msi_start; 27362306a36Sopenharmony_ci}; 27462306a36Sopenharmony_ci 27562306a36Sopenharmony_ci/* 27662306a36Sopenharmony_ci * A iommufd_device object represents the binding relationship between a 27762306a36Sopenharmony_ci * consuming driver and the iommufd. These objects are created/destroyed by 27862306a36Sopenharmony_ci * external drivers, not by userspace. 27962306a36Sopenharmony_ci */ 28062306a36Sopenharmony_cistruct iommufd_device { 28162306a36Sopenharmony_ci struct iommufd_object obj; 28262306a36Sopenharmony_ci struct iommufd_ctx *ictx; 28362306a36Sopenharmony_ci struct iommufd_group *igroup; 28462306a36Sopenharmony_ci struct list_head group_item; 28562306a36Sopenharmony_ci /* always the physical device */ 28662306a36Sopenharmony_ci struct device *dev; 28762306a36Sopenharmony_ci bool enforce_cache_coherency; 28862306a36Sopenharmony_ci}; 28962306a36Sopenharmony_ci 29062306a36Sopenharmony_cistatic inline struct iommufd_device * 29162306a36Sopenharmony_ciiommufd_get_device(struct iommufd_ucmd *ucmd, u32 id) 29262306a36Sopenharmony_ci{ 29362306a36Sopenharmony_ci return container_of(iommufd_get_object(ucmd->ictx, id, 29462306a36Sopenharmony_ci IOMMUFD_OBJ_DEVICE), 29562306a36Sopenharmony_ci struct iommufd_device, obj); 29662306a36Sopenharmony_ci} 29762306a36Sopenharmony_ci 29862306a36Sopenharmony_civoid iommufd_device_destroy(struct iommufd_object *obj); 29962306a36Sopenharmony_ciint iommufd_get_hw_info(struct iommufd_ucmd *ucmd); 30062306a36Sopenharmony_ci 30162306a36Sopenharmony_cistruct iommufd_access { 30262306a36Sopenharmony_ci struct iommufd_object obj; 30362306a36Sopenharmony_ci struct iommufd_ctx *ictx; 30462306a36Sopenharmony_ci struct iommufd_ioas *ioas; 30562306a36Sopenharmony_ci struct iommufd_ioas *ioas_unpin; 30662306a36Sopenharmony_ci struct mutex ioas_lock; 30762306a36Sopenharmony_ci const struct iommufd_access_ops *ops; 30862306a36Sopenharmony_ci void *data; 30962306a36Sopenharmony_ci unsigned long iova_alignment; 31062306a36Sopenharmony_ci u32 iopt_access_list_id; 31162306a36Sopenharmony_ci}; 31262306a36Sopenharmony_ci 31362306a36Sopenharmony_ciint iopt_add_access(struct io_pagetable *iopt, struct iommufd_access *access); 31462306a36Sopenharmony_civoid iopt_remove_access(struct io_pagetable *iopt, 31562306a36Sopenharmony_ci struct iommufd_access *access, 31662306a36Sopenharmony_ci u32 iopt_access_list_id); 31762306a36Sopenharmony_civoid iommufd_access_destroy_object(struct iommufd_object *obj); 31862306a36Sopenharmony_ci 31962306a36Sopenharmony_ci#ifdef CONFIG_IOMMUFD_TEST 32062306a36Sopenharmony_ciint iommufd_test(struct iommufd_ucmd *ucmd); 32162306a36Sopenharmony_civoid iommufd_selftest_destroy(struct iommufd_object *obj); 32262306a36Sopenharmony_ciextern size_t iommufd_test_memory_limit; 32362306a36Sopenharmony_civoid iommufd_test_syz_conv_iova_id(struct iommufd_ucmd *ucmd, 32462306a36Sopenharmony_ci unsigned int ioas_id, u64 *iova, u32 *flags); 32562306a36Sopenharmony_cibool iommufd_should_fail(void); 32662306a36Sopenharmony_ciint __init iommufd_test_init(void); 32762306a36Sopenharmony_civoid iommufd_test_exit(void); 32862306a36Sopenharmony_cibool iommufd_selftest_is_mock_dev(struct device *dev); 32962306a36Sopenharmony_ci#else 33062306a36Sopenharmony_cistatic inline void iommufd_test_syz_conv_iova_id(struct iommufd_ucmd *ucmd, 33162306a36Sopenharmony_ci unsigned int ioas_id, 33262306a36Sopenharmony_ci u64 *iova, u32 *flags) 33362306a36Sopenharmony_ci{ 33462306a36Sopenharmony_ci} 33562306a36Sopenharmony_cistatic inline bool iommufd_should_fail(void) 33662306a36Sopenharmony_ci{ 33762306a36Sopenharmony_ci return false; 33862306a36Sopenharmony_ci} 33962306a36Sopenharmony_cistatic inline int __init iommufd_test_init(void) 34062306a36Sopenharmony_ci{ 34162306a36Sopenharmony_ci return 0; 34262306a36Sopenharmony_ci} 34362306a36Sopenharmony_cistatic inline void iommufd_test_exit(void) 34462306a36Sopenharmony_ci{ 34562306a36Sopenharmony_ci} 34662306a36Sopenharmony_cistatic inline bool iommufd_selftest_is_mock_dev(struct device *dev) 34762306a36Sopenharmony_ci{ 34862306a36Sopenharmony_ci return false; 34962306a36Sopenharmony_ci} 35062306a36Sopenharmony_ci#endif 35162306a36Sopenharmony_ci#endif 352