iommufd: Add vIOMMU infrastructure (Part-4 HW QUEUE)
Get series with b4
b4 am [email protected]Versions newest first · linked by author and title
- v9 Latest29 patches 12 repliesIn review
- v829 patches 11 repliesSuperseded
- v728 patches 38 repliesSuperseded
Earlier versions · 6
| Version | Posted | Patches | Replies | Status |
|---|---|---|---|---|
| v6 | 25 patches | 51 replies | Superseded | |
| v5 | 29 patches | 49 replies | Superseded | |
| v4 | 23 patches | 81 replies | Superseded | |
| v3 | 23 patches | 17 replies | Superseded | |
| v2 | 22 patches | 123 replies | Superseded | |
| v1 | 16 patches | 35 replies | Superseded |
Patches in v9 No applies recorded yet
| # | Subject and files | Size | Replies | Applied |
|---|---|---|---|---|
| 1/29 | iommufd: Report unmapped bytes in the error path of iopt_unmap_iova_rangedrivers/ | +5 | 0 replies | |
| 2/29 | iommufd: Correct virt_id kdoc at struct iommu_vdevice_allocinclude/ | +1 | 0 replies | |
| 3/29 | iommufd/viommu: Explicitly define vdev->virt_iddrivers/ drivers/ drivers/ | +9 | 0 replies | |
| 4/29 | iommu: Use enum iommu_hw_info_type for type in hw_info opdrivers/ drivers/ drivers/ +2 more | +11 | 0 replies | |
| 5/29 | iommu: Add iommu_copy_struct_to_user helperinclude/ | +40 | 0 replies | |
| 6/29 | iommu: Pass in a driver-level user data structure to viommu_init opdrivers/ drivers/ drivers/ +2 more | +9 | 0 replies | |
| 7/29 | iommufd/viommu: Allow driver-specific user data for a vIOMMU objectdrivers/ include/ | +13 | 0 replies | |
| 8/29 | iommufd/selftest: Support user_data in mock_viommu_allocdrivers/ drivers/ | +28 | 0 replies | |
| 9/29 | iommufd/selftest: Add coverage for viommu datatools/ tools/ tools/ | +40 | 0 replies | |
| 10/29 | iommufd/access: Add internal APIs for HW queue to usedrivers/ drivers/ | +73 | 0 replies | |
| 11/29 | iommufd/access: Bypass access->ops->unmap for internal usedrivers/ drivers/ drivers/ +1 more | +31 | 0 replies | |
| 12/29 | iommufd/viommu: Add driver-defined vDEVICE supportdrivers/ drivers/ include/ | +56 | 0 replies | |
| 13/29 | iommufd/viommu: Introduce IOMMUFD_OBJ_HW_QUEUE and its related structinclude/ include/ | +51 | 0 replies | |
| 14/29 | iommufd/viommu: Add IOMMUFD_CMD_HW_QUEUE_ALLOC ioctldrivers/ drivers/ drivers/ +2 more | +222 | 0 replies | |
| 15/29 | iommufd/driver: Add iommufd_hw_queue_depend/undepend() helpersdrivers/ include/ | +72 | 0 replies | |
| 16/29 | iommufd/selftest: Add coverage for IOMMUFD_CMD_HW_QUEUE_ALLOCdrivers/ drivers/ tools/ +2 more | +196 | 1 reply | |
| 17/29 | iommufd: Add mmap interfacedrivers/ drivers/ drivers/ +1 more | +171 | 2 replies | |
| 18/29 | iommufd/selftest: Add coverage for the new mmap interfacedrivers/ drivers/ tools/ +1 more | +59 | 1 reply | |
| 19/29 | Documentation: userspace-api: iommufd: Update HW QUEUEDocumentation/ | +12 | 0 replies | |
| 20/29 | iommu: Allow an input type in hw_info opdrivers/ drivers/ drivers/ +3 more | +20 | 0 replies | |
| 21/29 | iommufd: Allow an input data_type via iommu_hw_infodrivers/ include/ | +25 | 0 replies | |
| 22/29 | iommufd/selftest: Update hw_info coverage for an input data_typetools/ tools/ tools/ | +46 | 5 replies | |
| 23/29 | iommu/arm-smmu-v3-iommufd: Add vsmmu_size/type and vsmmu_init impl opsdrivers/ drivers/ | +13 | 3 replies | |
| 24/29 | iommu/arm-smmu-v3-iommufd: Add hw_info to impl_opsdrivers/ drivers/ | +13 | 0 replies | |
| 25/29 | iommu/tegra241-cmdqv: Use request_threaded_irqdrivers/ | +3 | 0 replies | |
| 26/29 | iommu/tegra241-cmdqv: Simplify deinit flow in tegra241_cmdqv_remove_vintf()drivers/ | +3 | 0 replies | |
| 27/29 | iommu/tegra241-cmdqv: Do not statically map LVCMDQsdrivers/ | +33 | 0 replies | |
| 28/29 | iommu/tegra241-cmdqv: Add user-space use supportdrivers/ drivers/ drivers/ +1 more | +465 | 0 replies | |
| 29/29 | iommu/tegra241-cmdqv: Add IOMMU_VEVENTQ_TYPE_TEGRA241_CMDQV supportdrivers/ include/ | +37 | 0 replies |
Reviews trailers per patch
All 29 patches have a Reviewed-by or Acked-by.
| Patch | Kevin Tian | Jason Gunthorpe | Pranjal Shrivastava | Vasant Hegde | Lu Baolu | Alok Tiwari |
|---|---|---|---|---|---|---|
| 1/29 | R-b | R-b | ||||
| 2/29 | R-b | |||||
| 3/29 | R-b | R-b | R-b | R-b | ||
| 4/29 | R-b | R-b | R-b | |||
| 5/29 | R-b | R-b | R-b | R-b | ||
| 6/29 | R-b | R-b | R-b | R-b | R-b | |
| 7/29 | R-b | R-b | A-b | R-b | R-b | A-b |
| 8/29 | R-b | R-b | ||||
| 9/29 | R-b | R-b | ||||
| 10/29 | R-b | R-b | ||||
| 11/29 | R-b | R-b | R-b | R-b | ||
| 12/29 | R-b | R-b | R-b | R-b | R-b | |
| 13/29 | R-b | R-b | R-b | R-b | R-b | |
| 14/29 | R-b | R-b | R-b | |||
| 15/29 | R-b | R-b | R-b | |||
| 16/29 | R-b | |||||
| 17/29 | R-b | R-b | R-b | R-b | ||
| 18/29 | R-b | |||||
| 19/29 | R-b | R-b | R-b | |||
| 20/29 | R-b | R-b | R-b | R-b | ||
| 21/29 | R-b | R-b | R-b | R-b | ||
| 22/29 | R-b | |||||
| 23/29 | R-b | R-b | R-b | |||
| 24/29 | R-b | R-b | ||||
| 25/29 | R-b | R-b | A-b | |||
| 26/29 | R-b | R-b | A-b | |||
| 27/29 | R-b | A-b | ||||
| 28/29 | R-b | R-b | ||||
| 29/29 | R-b | R-b | R-b |
Trailers given in replies are filled; those carried in the patches from earlier versions are outlined with dashes. Scroll the table sideways for all 6 reviewers.
Cover letter [PATCH v9 00/29] iommufd: Add vIOMMU infrastructure (Part-4 HW QUEUE)
The vIOMMU object is designed to represent a slice of an IOMMU HW for its virtualization features shared with or passed to user space (a VM mostly) in a way of HW acceleration. This extended the HWPT-based design for more advanced virtualization feature.
HW QUEUE introduced by this series as a part of the vIOMMU infrastructure represents a HW accelerated queue/buffer for VM to use exclusively, e.g.
- NVIDIA's Virtual Command Queue
- AMD vIOMMU's Command Buffer, Event Log Buffer, and PPR Log Buffer
each of which allows its IOMMU HW to directly access a queue memory owned by a guest VM and allows a guest OS to control the HW queue direclty, to avoid VM Exit overheads to improve the performance.
Introduce IOMMUFD_OBJ_HW_QUEUE and its pairing IOMMUFD_CMD_HW_QUEUE_ALLOC allowing VMM to forward the IOMMU-specific queue info, such as queue base address, size, and etc.
Meanwhile, a guest-owned queue needs the guest kernel to control the queue by reading/writing its consumer and producer indexes, via MMIO acceses to the hardware MMIO registers. Introduce an mmap infrastructure for iommufd to support passing through a piece of MMIO region from the host physical address space to the guest physical address space. The mmap info (offset/ length) used by an mmap syscall must be pre-allocated and returned to the user space via an output driver-data during an IOMMUFD_CMD_HW_QUEUE_ALLOC call. Thus, it requires a driver-specific user data support in the vIOMMU allocation flow.
As a real-world use case, this series implements a HW QUEUE support in the tegra241-cmdqv driver for VCMDQs on NVIDIA Grace CPU. In another word, it is also the Tegra CMDQV series Part-2 (user-space support), reworked from Previous RFCv1:
https://lore.kernel.org/all/[email protected]/
This enables the HW accelerated feature for NVIDIA Grace CPU. Compared to the standard SMMUv3 operating in the nested translation mode trapping CMDQ for TLBI and ATC_INV commands, this gives a huge performance improvement:
70% to 90% reductions of invalidation time were measured by various DMA unmap tests running in a guest OS.
// Unmap latencies from "dma_map_benchmark -g @granule -t @threads", // by toggling "/sys/kernel/debug/iommu/tegra241_cmdqv/bypass_vcmdq" @granule | @threads | bypass_vcmdq=1 | bypass_vcmdq=0
4KB 1 35.7 us 5.3 us
16KB 1 41.8 us 6.8 us
64KB 1 68.9 us 9.9 us
128KB 1 109.0 us 12.6 us
256KB 1 187.1 us 18.0 us
4KB 2 96.9 us 6.8 us
16KB 2 97.8 us 7.5 us
64KB 2 151.5 us 10.7 us
128KB 2 257.8 us 12.7 us
256KB 2 443.0 us 17.9 usThis is on Github:
https://github.com/nicolinc/iommufd/commits/iommufd_hw_queue-v9
Paring QEMU branch for testing (reusing v8):
https://github.com/nicolinc/qemu/commits/wip/for_iommufd_hw_queue-v8
Changelog
v9 (attached git-diff v8..v9 at the end of this letter)
* Add Reviewed-by from Vasant and Jason
* [iommufd] Fix offset calculation
* [iommufd] Add unaligned iova/length selftest coverage for hw_queue
* [iommufd] Pass in aligned iova/length to iommufd_access_pin_pages()
* [smmu] Change "u32 *type" at arm_smmu_hw_info() in the header
v8
https://lore.kernel.org/all/[email protected]/
* Add Reviewed-by from Pranj, Kevin and Jason
* Improve kdoc and comments
* [iommufd] Skip selftest for no_viommu variants
* [iommufd] Add unmap coverage for non internal area
* [iommufd] Skip the first page when mtree_alloc_range()
* [iommufd] Correct the passed in index to mtree_erase()
* [iommufd] Correct variable types in iommufd_hw_queue_alloc_phys()
* [iommufd] Reject iopt_unmap_iova_range() if area->num_locks is set
* [tegra] Rename "SID replacement" with "SID mapping"
* [tegra] Unwrap useless _tegra241_vcmdq_hw_init helper
v7
https://lore.kernel.org/all/[email protected]/
* Rebased on Jason's for-next tree (iommufd_hw_queue-prep series)
* Add Reviewed-by from Baolu, Jason, Pranjal
* Update kdocs and notes
* [iommu] Replace "u32" with "enum iommu_hw_info_type"
* [iommufd] Rename vdev->id to vdev->virt_id
* [iommufd] Replace macros with inline helpers
* [iommufd] Report unmapped_bytes in error path
* [iommufd] Add iommufd_access_is_internal helper
* [iommufd] Do not drop ops->unmap check for mdevs
* [iommufd] Store physical addresses in immap structure
* [iommufd] Reorder access and hw_queue object allocations
* [iommufd] Scan for an internal access before any unmap call
* [iommufd] Drop unused ictx pointer in struct iommufd_hw_queue
* [iommufd] Use kcalloc to avoid failure due to memory fragmentation
* [tegra] Use "else"
* [tegra] Lock destroy() using lvcmdq_mutex
v6
https://lore.kernel.org/all/[email protected]/
* Rebase on iommufd_hw_queue-prep-v2
* Add Reviewed-by from Kevin and Jason
* [iommufd] Update kdocs and notes
* [iommufd] Drop redundant pages[i] check
* [iommufd] Allow nesting_parent_iova to be 0
* [iommufd] Add iommufd_hw_queue_alloc_phys()
* [iommufd] Revise iommufd_viommu_alloc/destroy_mmap APIs
* [iommufd] Move destroy ops to vdevice/hw_queue structures
* [iommufd] Add union in hw_info struct to share out_data_type field
* [iommufd] Replace iopt_pin/unpin_pages() with internal access APIs
* [iommufd] Replace vdevice_alloc with vdevice_size and vdevice_init
* [iommufd] Replace hw_queue_alloc with get_hw_queue_size/hw_queue_init
* [iommufd] Replace IOMMUFD_VIOMMU_FLAG_HW_QUEUE_READS_PA with init_phys
* [smmu] Drop arm_smmu_domain_ipa_to_pa
* [smmu] Update arm_smmu_impl_ops changes for vsmmu_init
* [tegra] Add a vdev_to_vsid macro
* [tegra] Add lvcmdq_mutex to protect multi queues
* [tegra] Drop duplicated kcalloc for vintf->lvcmdqs (memory leak)
v5
https://lore.kernel.org/all/[email protected]/
* Rebase on v6.15-rc6
* Add Reviewed-by from Jason and Kevin
* Correct typos in kdoc and update commit logs
* [iommufd] Add a cosmetic fix
* [iommufd] Drop unused num_pfns
* [iommufd] Drop unnecessary check
* [iommufd] Reorder patch sequence
* [iommufd] Use io_remap_pfn_range()
* [iommufd] Use success oriented flow
* [iommufd] Fix max_npages calculation
* [iommufd] Add more selftest coverage
* [iommufd] Drop redundant static_assert
* [iommufd] Fix mmap pfn range validation
* [iommufd] Reject unmap on pinned iovas
* [iommufd] Drop redundant vm_flags_set()
* [iommufd] Drop iommufd_struct_destroy()
* [iommufd] Drop redundant queue iova test
* [iommufd] Use "mmio_addr" and "mmio_pfn"
* [iommufd] Rename to "nesting_parent_iova"
* [iommufd] Make iopt_pin_pages call option
* [iommufd] Add ictx comparison in depend()
* [iommufd] Add iommufd_object_alloc_ucmd()
* [iommufd] Move kcalloc() after validations
* [iommufd] Replace ictx setting with WARN_ON
* [iommufd] Make hw_info's type bidirectional
* [smmu] Add supported_vsmmu_type in impl_ops
* [smmu] Drop impl report in smmu vendor struct
* [tegra] Add IOMMU_HW_INFO_TYPE_TEGRA241_CMDQV
* [tegra] Replace "number of VINTFs" with a note
* [tegra] Drop the redundant lvcmdq pointer setting
* [tegra] Flag IOMMUFD_VIOMMU_FLAG_HW_QUEUE_READS_PA
* [tegra] Use "vintf_alloc_vsid" for vdevice_alloc op
v4
https://lore.kernel.org/all/[email protected]/
* Rebase on v6.15-rc5
* Add Reviewed-by from Vasant
* Rename "vQUEUE" to "HW QUEUE"
* Use "offset" and "length" for all mmap-related variables
* [iommufd] Use u64 for guest PA
* [iommufd] Fix typo in uAPI doc
* [iommufd] Rename immap_id to offset
* [iommufd] Drop the partial-size mmap support
* [iommufd] Do not replace WARN_ON with WARN_ON_ONCE
* [iommufd] Use "u64 base_addr" for queue base address
* [iommufd] Use u64 base_pfn/num_pfns for immap structure
* [iommufd] Correct the size passed in to mtree_alloc_range()
* [iommufd] Add IOMMUFD_VIOMMU_FLAG_HW_QUEUE_READS_PA to viommu_ops
v3
https://lore.kernel.org/all/[email protected]/
* Add Reviewed-by from Baolu, Pranjal, and Alok
* Revise kdocs, uAPI docs, and commit logs
* Rename "vCMDQ" back to "vQUEUE" for AMD cases
* [tegra] Add tegra241_vcmdq_hw_flush_timeout()
* [tegra] Rename vsmmu_alloc to alloc_vintf_user
* [tegra] Use writel for SID replacement registers
* [tegra] Move mmap removal call to vsmmu_destroy op
* [tegra] Fix revert in tegra241_vintf_alloc_lvcmdq_user()
* [iommufd] Replace "& ~PAGE_MASK" with PAGE_ALIGNED()
* [iommufd] Add an object-type "owner" to immap structure
* [iommufd] Drop the ictx input in the new for-driver APIs
* [iommufd] Add iommufd_vma_ops to keep track of mmap lifecycle
* [iommufd] Add viommu-based iommufd_viommu_alloc/destroy_mmap helpers
* [iommufd] Rename iommufd_ctx_alloc/free_mmap to _iommufd_alloc/destroy_mmap
v2
https://lore.kernel.org/all/[email protected]/
* Add Reviewed-by from Jason
* [smmu] Fix vsmmu initial value
* [smmu] Support impl for hw_info
* [tegra] Rename "slot" to "vsid"
* [tegra] Update kdocs and commit logs
* [tegra] Map/unmap LVCMDQ dynamically
* [tegra] Refcount the previous LVCMDQ
* [tegra] Return -EEXIST if LVCMDQ exists
* [tegra] Simplify VINTF cleanup routine
* [tegra] Use vmid and s2_domain in vsmmu
* [tegra] Rename "mmap_pgoff" to "immap_id"
* [tegra] Add more addr and length validation
* [iommufd] Add more narrative to mmap's kdoc
* [iommufd] Add iommufd_struct_depend/undepend()
* [iommufd] Rename vcmdq_free op to vcmdq_destroy
* [iommufd] Fix bug in iommu_copy_struct_to_user()
* [iommufd] Drop is_io from iommufd_ctx_alloc_mmap()
* [iommufd] Test the queue memory for its contiguity
* [iommufd] Return -ENXIO if address or length fails
* [iommufd] Do not change @min_last in mock_viommu_alloc()
* [iommufd] Generalize TEGRA241_VCMDQ data in core structure
* [iommufd] Add selftest coverage for IOMMUFD_CMD_VCMDQ_ALLOC
* [iommufd] Add iopt_pin_pages() to prevent queue memory from unmapping
v1
https://lore.kernel.org/all/[email protected]/
Thanks
Nicolin
Nicolin Chen (29):
iommufd: Report unmapped bytes in the error path of
iopt_unmap_iova_range
iommufd: Correct virt_id kdoc at struct iommu_vdevice_alloc iommufd/viommu: Explicitly define vdev->virt_id
iommu: Use enum iommu_hw_info_type for type in hw_info op
iommu: Add iommu_copy_struct_to_user helper
iommu: Pass in a driver-level user data structure to viommu_init op iommufd/viommu: Allow driver-specific user data for a vIOMMU object iommufd/selftest: Support user_data in mock_viommu_alloc iommufd/selftest: Add coverage for viommu data iommufd/access: Add internal APIs for HW queue to use iommufd/access: Bypass access->ops->unmap for internal use iommufd/viommu: Add driver-defined vDEVICE support iommufd/viommu: Introduce IOMMUFD_OBJ_HW_QUEUE and its related struct iommufd/viommu: Add IOMMUFD_CMD_HW_QUEUE_ALLOC ioctl iommufd/driver: Add iommufd_hw_queue_depend/undepend() helpers iommufd/selftest: Add coverage for IOMMUFD_CMD_HW_QUEUE_ALLOC
iommufd: Add mmap interface
iommufd/selftest: Add coverage for the new mmap interface
Documentation: userspace-api: iommufd: Update HW QUEUE
iommu: Allow an input type in hw_info op
iommufd: Allow an input data_type via iommu_hw_info iommufd/selftest: Update hw_info coverage for an input data_type iommu/arm-smmu-v3-iommufd: Add vsmmu_size/type and vsmmu_init impl ops iommu/arm-smmu-v3-iommufd: Add hw_info to impl_ops iommu/tegra241-cmdqv: Use request_threaded_irq iommu/tegra241-cmdqv: Simplify deinit flow in
tegra241_cmdqv_remove_vintf()
iommu/tegra241-cmdqv: Do not statically map LVCMDQs iommu/tegra241-cmdqv: Add user-space use support iommu/tegra241-cmdqv: Add IOMMU_VEVENTQ_TYPE_TEGRA241_CMDQV support
drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3.h | 25 +- drivers/iommu/iommufd/io_pagetable.h | 5 +- drivers/iommu/iommufd/iommufd_private.h | 46 +- drivers/iommu/iommufd/iommufd_test.h | 20 + include/linux/iommu.h | 50 +- include/linux/iommufd.h | 160 ++++++ include/uapi/linux/iommufd.h | 147 +++++- tools/testing/selftests/iommu/iommufd_utils.h | 89 +++- .../arm/arm-smmu-v3/arm-smmu-v3-iommufd.c | 28 +- .../iommu/arm/arm-smmu-v3/tegra241-cmdqv.c | 477 +++++++++++++++++- drivers/iommu/intel/iommu.c | 7 +- drivers/iommu/iommufd/device.c | 87 +++- drivers/iommu/iommufd/driver.c | 82 ++- drivers/iommu/iommufd/io_pagetable.c | 13 +- drivers/iommu/iommufd/main.c | 69 +++ drivers/iommu/iommufd/pages.c | 12 +- drivers/iommu/iommufd/selftest.c | 153 +++++- drivers/iommu/iommufd/viommu.c | 218 +++++++- tools/testing/selftests/iommu/iommufd.c | 141 +++++- .../selftests/iommu/iommufd_fail_nth.c | 15 +- Documentation/userspace-api/iommufd.rst | 12 + 21 files changed, 1745 insertions(+), 111 deletions(-)
Signature · 1 line
2.43.0
drivers/iommu/arm/arm-smmu-v3/arm-smmu-v3.h +2 -1
@@ -1045,7 +1045,8 @@ struct arm_vsmmu { };#if IS_ENABLED (CONFIG_ARM_SMMU_V3_IOMMUFD ) -void *arm_smmu_hw_info (struct device *dev,u32 *length,u32 *type); +void *arm_smmu_hw_info (struct device *dev,u32 *length, +enum iommu_hw_info_type *type);size_t arm_smmu_get_viommu_size (struct device *dev,enum iommu_viommu_type viommu_type); int arm_vsmmu_init(struct iommufd_viommu *viommu,
drivers/iommu/iommufd/viommu.c +13 -10
@@ -206,7 +206,11 @@ static void iommufd_hw_queue_destroy_access(struct iommufd_ctx *ictx,struct iommufd_access *access, u64 base_iova, size_t length) { -iommufd_access_unpin_pages (access ,base_iova ,length ); + u64 aligned_iova = PAGE_ALIGN_DOWN(base_iova); +u64 offset = base_iova - aligned_iova; + +iommufd_access_unpin_pages (access, aligned_iova, +PAGE_ALIGN (length + offset));iommufd_access_detach_internal (access);iommufd_access_destroy_internal (ictx, access); }
@@ -239,22 +243,23 @@ static struct iommufd_access * iommufd_hw_queue_alloc_phys(struct iommu_hw_queue_alloc *cmd, struct iommufd_viommu *viommu, phys_addr_t *base_pa) { + u64 aligned_iova = PAGE_ALIGN_DOWN(cmd->nesting_parent_iova); +u64 offset = cmd->nesting_parent_iova - aligned_iova;struct iommufd_access *access;struct page **pages;size_t max_npages;size_t length; -u64 offset;size_t i;int rc; - offset = - cmd->nesting_parent_iova -PAGE_ALIGN (cmd->nesting_parent_iova); -/* DIV_ROUND_UP(offset + cmd->length, PAGE_SIZE) */ +/* max_npages = DIV_ROUND_UP(offset + cmd->length, PAGE_SIZE) */ if (check_add_overflow (offset, cmd->length, &length))return ERR_PTR (-ERANGE );if (check_add_overflow (length,PAGE_SIZE -1 , &length))return ERR_PTR (-ERANGE ); max_npages = length /PAGE_SIZE ; +/* length needs to be page aligned too */ + length = max_npages *PAGE_SIZE ;/* * Use kvcalloc() to avoid memory fragmentation for a large page array.
@@ -274,8 +279,7 @@ iommufd_hw_queue_alloc_phys(struct iommu_hw_queue_alloc *cmd,if (rc) goto out_destroy; - rc =iommufd_access_pin_pages (access, cmd->nesting_parent_iova, - cmd->length, pages,0 ); + rc =iommufd_access_pin_pages (access, aligned_iova, length, pages,0 );if (rc) goto out_detach;
@@ -287,13 +291,12 @@ iommufd_hw_queue_alloc_phys(struct iommu_hw_queue_alloc *cmd, goto out_unpin; } - *base_pa =page_to_pfn (pages[0 ]) <<PAGE_SHIFT ; + *base_pa = (page_to_pfn (pages[0 ]) <<PAGE_SHIFT ) + offset;kfree (pages);return access; out_unpin: -iommufd_access_unpin_pages (access, cmd->nesting_parent_iova, - cmd->length); +iommufd_access_unpin_pages (access, aligned_iova, length); out_detach:iommufd_access_detach_internal (access); out_destroy:
tools/testing/selftests/iommu/iommufd.c +5 -4
@@ -3104,17 +3104,18 @@ TEST_F(iommufd_viommu, hw_queue)/* Allocate index=0, declare ownership of the iova */ test_cmd_hw_queue_alloc (viommu_id,IOMMU_HW_QUEUE_TYPE_SELFTEST ,0 , iova,PAGE_SIZE , &hw_queue_id[0 ]); -/* Fail duplicate */ +/* Fail duplicated index */ test_err_hw_queue_alloc (EEXIST , viommu_id,IOMMU_HW_QUEUE_TYPE_SELFTEST ,0 , iova,PAGE_SIZE , &hw_queue_id[0 ]);/* Fail unmap, due to iova ownership */ test_err_ioctl_ioas_unmap (EBUSY , iova,PAGE_SIZE );/* The 2nd page is not pinned, so it can be unmmap */ -test_ioctl_ioas_unmap (iova +PAGE_SIZE ,PAGE_SIZE ); +test_ioctl_ioas_unmap (iova2,PAGE_SIZE ); -/* Allocate index=1 */ +/* Allocate index=1, with an unaligned case */ test_cmd_hw_queue_alloc (viommu_id,IOMMU_HW_QUEUE_TYPE_SELFTEST ,1 , - iova,PAGE_SIZE , &hw_queue_id[1 ]); + iova +PAGE_SIZE /2 ,PAGE_SIZE /2 , + &hw_queue_id[1 ]);/* Fail to destroy, due to dependency */ EXPECT_ERRNO (EBUSY ,_test_ioctl_destroy (self->fd, hw_queue_id[0 ]));