Pull iommufd updates from Jason Gunthorpe: - The iova_bitmap logic for efficiently reporting dirty pages back to userspace has a few more tricky corner case bugs that have been resolved and backed with new tests. The revised version has simpler logic. - Shared branch with iommu for handle support when doing domain attach. Handles allow the domain owner to include additional private data on a per-device basis. - IO Page Fault Reporting to userspace via iommufd. Page faults can be generated on fault capable HWPTs when a translation is not present. Routing them to userspace would allow a VMM to be able to virtualize them into an emulated vIOMMU. This is the next step to fully enabling vSVA support. * tag 'for-linus-iommufd' of git://git.kernel.org/pub/scm/linux/kernel/git/jgg/iommufd: (26 commits) iommufd: Put constants for all the uAPI enums iommufd: Fix error pointer checking iommufd: Add check on user response code iommufd: Remove IOMMUFD_PAGE_RESP_FAILURE iommufd: Require drivers to supply the cache_invalidate_user ops iommufd/selftest: Add coverage for IOPF test iommufd/selftest: Add IOPF support for mock device iommufd: Associate fault object with iommufd_hw_pgtable iommufd: Fault-capable hwpt attach/detach/replace iommufd: Add iommufd fault object iommufd: Add fault and response message definitions iommu: Extend domain attach group with handle support iommu: Add attach handle to struct iopf_group iommu: Remove sva handle list iommu: Introduce domain attachment handle iommufd/iova_bitmap: Remove iterator logic iommufd/iova_bitmap: Dynamic pinning on iova_bitmap_set() iommufd/iova_bitmap: Consolidate iova_bitmap_set exit conditionals iommufd/iova_bitmap: Move initial pinning to iova_bitmap_for_each() iommufd/iova_bitmap: Cache mapped length in iova_bitmap_map struct ...
Showing the changes to include/uapi (1 of 19 files). Show all
Unified · Split
| @@ -37,19 +37,20 @@ · 36 unmodified lines | |||
| 37 | enum { | 37 | enum { |
| 38 | IOMMUFD_CMD_BASE = 0x80, | 38 | IOMMUFD_CMD_BASE = 0x80, |
| 39 | IOMMUFD_CMD_DESTROY = IOMMUFD_CMD_BASE, | 39 | IOMMUFD_CMD_DESTROY = IOMMUFD_CMD_BASE, |
| 40 | IOMMUFD_CMD_IOAS_ALLOC, | 40 | IOMMUFD_CMD_IOAS_ALLOC = 0x81, |
| 41 | IOMMUFD_CMD_IOAS_ALLOW_IOVAS, | 41 | IOMMUFD_CMD_IOAS_ALLOW_IOVAS = 0x82, |
| 42 | IOMMUFD_CMD_IOAS_COPY, | 42 | IOMMUFD_CMD_IOAS_COPY = 0x83, |
| 43 | IOMMUFD_CMD_IOAS_IOVA_RANGES, | 43 | IOMMUFD_CMD_IOAS_IOVA_RANGES = 0x84, |
| 44 | IOMMUFD_CMD_IOAS_MAP, | 44 | IOMMUFD_CMD_IOAS_MAP = 0x85, |
| 45 | IOMMUFD_CMD_IOAS_UNMAP, | 45 | IOMMUFD_CMD_IOAS_UNMAP = 0x86, |
| 46 | IOMMUFD_CMD_OPTION, | 46 | IOMMUFD_CMD_OPTION = 0x87, |
| 47 | IOMMUFD_CMD_VFIO_IOAS, | 47 | IOMMUFD_CMD_VFIO_IOAS = 0x88, |
| 48 | IOMMUFD_CMD_HWPT_ALLOC, | 48 | IOMMUFD_CMD_HWPT_ALLOC = 0x89, |
| 49 | IOMMUFD_CMD_GET_HW_INFO, | 49 | IOMMUFD_CMD_GET_HW_INFO = 0x8a, |
| 50 | IOMMUFD_CMD_HWPT_SET_DIRTY_TRACKING, | 50 | IOMMUFD_CMD_HWPT_SET_DIRTY_TRACKING = 0x8b, |
| 51 | IOMMUFD_CMD_HWPT_GET_DIRTY_BITMAP, | 51 | IOMMUFD_CMD_HWPT_GET_DIRTY_BITMAP = 0x8c, |
| 52 | IOMMUFD_CMD_HWPT_INVALIDATE, | 52 | IOMMUFD_CMD_HWPT_INVALIDATE = 0x8d, |
| 53 | IOMMUFD_CMD_FAULT_QUEUE_ALLOC = 0x8e, | ||
| 53 | }; | 54 | }; |
| 54 | 55 | ||
| 55 | /** | 56 | /** |
| @@ -356,10 +357,13 @@ struct iommu_vfio_ioas { · 300 unmodified lines | |||
| 356 | * the parent HWPT in a nesting configuration. | 357 | * the parent HWPT in a nesting configuration. |
| 357 | * @IOMMU_HWPT_ALLOC_DIRTY_TRACKING: Dirty tracking support for device IOMMU is | 358 | * @IOMMU_HWPT_ALLOC_DIRTY_TRACKING: Dirty tracking support for device IOMMU is |
| 358 | * enforced on device attachment | 359 | * enforced on device attachment |
| 360 | * @IOMMU_HWPT_FAULT_ID_VALID: The fault_id field of hwpt allocation data is | ||
| 361 | * valid. | ||
| 359 | */ | 362 | */ |
| 360 | enum iommufd_hwpt_alloc_flags { | 363 | enum iommufd_hwpt_alloc_flags { |
| 361 | IOMMU_HWPT_ALLOC_NEST_PARENT = 1 << 0, | 364 | IOMMU_HWPT_ALLOC_NEST_PARENT = 1 << 0, |
| 362 | IOMMU_HWPT_ALLOC_DIRTY_TRACKING = 1 << 1, | 365 | IOMMU_HWPT_ALLOC_DIRTY_TRACKING = 1 << 1, |
| 366 | IOMMU_HWPT_FAULT_ID_VALID = 1 << 2, | ||
| 363 | }; | 367 | }; |
| 364 | 368 | ||
| 365 | /** | 369 | /** |
| @@ -396,8 +400,8 @@ struct iommu_hwpt_vtd_s1 { · 30 unmodified lines | |||
| 396 | * @IOMMU_HWPT_DATA_VTD_S1: Intel VT-d stage-1 page table | 400 | * @IOMMU_HWPT_DATA_VTD_S1: Intel VT-d stage-1 page table |
| 397 | */ | 401 | */ |
| 398 | enum iommu_hwpt_data_type { | 402 | enum iommu_hwpt_data_type { |
| 399 | IOMMU_HWPT_DATA_NONE, | 403 | IOMMU_HWPT_DATA_NONE = 0, |
| 400 | IOMMU_HWPT_DATA_VTD_S1, | 404 | IOMMU_HWPT_DATA_VTD_S1 = 1, |
| 401 | }; | 405 | }; |
| 402 | 406 | ||
| 403 | /** | 407 | /** |
| @@ -411,6 +415,9 @@ enum iommu_hwpt_data_type { · 7 unmodified lines | |||
| 411 | * @data_type: One of enum iommu_hwpt_data_type | 415 | * @data_type: One of enum iommu_hwpt_data_type |
| 412 | * @data_len: Length of the type specific data | 416 | * @data_len: Length of the type specific data |
| 413 | * @data_uptr: User pointer to the type specific data | 417 | * @data_uptr: User pointer to the type specific data |
| 418 | * @fault_id: The ID of IOMMUFD_FAULT object. Valid only if flags field of | ||
| 419 | * IOMMU_HWPT_FAULT_ID_VALID is set. | ||
| 420 | * @__reserved2: Padding to 64-bit alignment. Must be 0. | ||
| 414 | * | 421 | * |
| 415 | * Explicitly allocate a hardware page table object. This is the same object | 422 | * Explicitly allocate a hardware page table object. This is the same object |
| 416 | * type that is returned by iommufd_device_attach() and represents the | 423 | * type that is returned by iommufd_device_attach() and represents the |
| @@ -441,6 +448,8 @@ struct iommu_hwpt_alloc { · 24 unmodified lines | |||
| 441 | __u32 data_type; | 448 | __u32 data_type; |
| 442 | __u32 data_len; | 449 | __u32 data_len; |
| 443 | __aligned_u64 data_uptr; | 450 | __aligned_u64 data_uptr; |
| 451 | __u32 fault_id; | ||
| 452 | __u32 __reserved2; | ||
| 444 | }; | 453 | }; |
| 445 | #define IOMMU_HWPT_ALLOC _IO(IOMMUFD_TYPE, IOMMUFD_CMD_HWPT_ALLOC) | 454 | #define IOMMU_HWPT_ALLOC _IO(IOMMUFD_TYPE, IOMMUFD_CMD_HWPT_ALLOC) |
| 446 | 455 | ||
| @@ -482,8 +491,8 @@ struct iommu_hw_info_vtd { · 35 unmodified lines | |||
| 482 | * @IOMMU_HW_INFO_TYPE_INTEL_VTD: Intel VT-d iommu info type | 491 | * @IOMMU_HW_INFO_TYPE_INTEL_VTD: Intel VT-d iommu info type |
| 483 | */ | 492 | */ |
| 484 | enum iommu_hw_info_type { | 493 | enum iommu_hw_info_type { |
| 485 | IOMMU_HW_INFO_TYPE_NONE, | 494 | IOMMU_HW_INFO_TYPE_NONE = 0, |
| 486 | IOMMU_HW_INFO_TYPE_INTEL_VTD, | 495 | IOMMU_HW_INFO_TYPE_INTEL_VTD = 1, |
| 487 | }; | 496 | }; |
| 488 | 497 | ||
| 489 | /** | 498 | /** |
| @@ -620,7 +629,7 @@ struct iommu_hwpt_get_dirty_bitmap { · 130 unmodified lines | |||
| 620 | * @IOMMU_HWPT_INVALIDATE_DATA_VTD_S1: Invalidation data for VTD_S1 | 629 | * @IOMMU_HWPT_INVALIDATE_DATA_VTD_S1: Invalidation data for VTD_S1 |
| 621 | */ | 630 | */ |
| 622 | enum iommu_hwpt_invalidate_data_type { | 631 | enum iommu_hwpt_invalidate_data_type { |
| 623 | IOMMU_HWPT_INVALIDATE_DATA_VTD_S1, | 632 | IOMMU_HWPT_INVALIDATE_DATA_VTD_S1 = 0, |
| 624 | }; | 633 | }; |
| 625 | 634 | ||
| 626 | /** | 635 | /** |
| @@ -692,4 +701,100 @@ struct iommu_hwpt_invalidate { · 65 unmodified lines | |||
| 692 | __u32 __reserved; | 701 | __u32 __reserved; |
| 693 | }; | 702 | }; |
| 694 | #define IOMMU_HWPT_INVALIDATE _IO(IOMMUFD_TYPE, IOMMUFD_CMD_HWPT_INVALIDATE) | 703 | #define IOMMU_HWPT_INVALIDATE _IO(IOMMUFD_TYPE, IOMMUFD_CMD_HWPT_INVALIDATE) |
| 704 | |||
| 705 | /** | ||
| 706 | * enum iommu_hwpt_pgfault_flags - flags for struct iommu_hwpt_pgfault | ||
| 707 | * @IOMMU_PGFAULT_FLAGS_PASID_VALID: The pasid field of the fault data is | ||
| 708 | * valid. | ||
| 709 | * @IOMMU_PGFAULT_FLAGS_LAST_PAGE: It's the last fault of a fault group. | ||
| 710 | */ | ||
| 711 | enum iommu_hwpt_pgfault_flags { | ||
| 712 | IOMMU_PGFAULT_FLAGS_PASID_VALID = (1 << 0), | ||
| 713 | IOMMU_PGFAULT_FLAGS_LAST_PAGE = (1 << 1), | ||
| 714 | }; | ||
| 715 | |||
| 716 | /** | ||
| 717 | * enum iommu_hwpt_pgfault_perm - perm bits for struct iommu_hwpt_pgfault | ||
| 718 | * @IOMMU_PGFAULT_PERM_READ: request for read permission | ||
| 719 | * @IOMMU_PGFAULT_PERM_WRITE: request for write permission | ||
| 720 | * @IOMMU_PGFAULT_PERM_EXEC: (PCIE 10.4.1) request with a PASID that has the | ||
| 721 | * Execute Requested bit set in PASID TLP Prefix. | ||
| 722 | * @IOMMU_PGFAULT_PERM_PRIV: (PCIE 10.4.1) request with a PASID that has the | ||
| 723 | * Privileged Mode Requested bit set in PASID TLP | ||
| 724 | * Prefix. | ||
| 725 | */ | ||
| 726 | enum iommu_hwpt_pgfault_perm { | ||
| 727 | IOMMU_PGFAULT_PERM_READ = (1 << 0), | ||
| 728 | IOMMU_PGFAULT_PERM_WRITE = (1 << 1), | ||
| 729 | IOMMU_PGFAULT_PERM_EXEC = (1 << 2), | ||
| 730 | IOMMU_PGFAULT_PERM_PRIV = (1 << 3), | ||
| 731 | }; | ||
| 732 | |||
| 733 | /** | ||
| 734 | * struct iommu_hwpt_pgfault - iommu page fault data | ||
| 735 | * @flags: Combination of enum iommu_hwpt_pgfault_flags | ||
| 736 | * @dev_id: id of the originated device | ||
| 737 | * @pasid: Process Address Space ID | ||
| 738 | * @grpid: Page Request Group Index | ||
| 739 | * @perm: Combination of enum iommu_hwpt_pgfault_perm | ||
| 740 | * @addr: Fault address | ||
| 741 | * @length: a hint of how much data the requestor is expecting to fetch. For | ||
| 742 | * example, if the PRI initiator knows it is going to do a 10MB | ||
| 743 | * transfer, it could fill in 10MB and the OS could pre-fault in | ||
| 744 | * 10MB of IOVA. It's default to 0 if there's no such hint. | ||
| 745 | * @cookie: kernel-managed cookie identifying a group of fault messages. The | ||
| 746 | * cookie number encoded in the last page fault of the group should | ||
| 747 | * be echoed back in the response message. | ||
| 748 | */ | ||
| 749 | struct iommu_hwpt_pgfault { | ||
| 750 | __u32 flags; | ||
| 751 | __u32 dev_id; | ||
| 752 | __u32 pasid; | ||
| 753 | __u32 grpid; | ||
| 754 | __u32 perm; | ||
| 755 | __u64 addr; | ||
| 756 | __u32 length; | ||
| 757 | __u32 cookie; | ||
| 758 | }; | ||
| 759 | |||
| 760 | /** | ||
| 761 | * enum iommufd_page_response_code - Return status of fault handlers | ||
| 762 | * @IOMMUFD_PAGE_RESP_SUCCESS: Fault has been handled and the page tables | ||
| 763 | * populated, retry the access. This is the | ||
| 764 | * "Success" defined in PCI 10.4.2.1. | ||
| 765 | * @IOMMUFD_PAGE_RESP_INVALID: Could not handle this fault, don't retry the | ||
| 766 | * access. This is the "Invalid Request" in PCI | ||
| 767 | * 10.4.2.1. | ||
| 768 | */ | ||
| 769 | enum iommufd_page_response_code { | ||
| 770 | IOMMUFD_PAGE_RESP_SUCCESS = 0, | ||
| 771 | IOMMUFD_PAGE_RESP_INVALID = 1, | ||
| 772 | }; | ||
| 773 | |||
| 774 | /** | ||
| 775 | * struct iommu_hwpt_page_response - IOMMU page fault response | ||
| 776 | * @cookie: The kernel-managed cookie reported in the fault message. | ||
| 777 | * @code: One of response code in enum iommufd_page_response_code. | ||
| 778 | */ | ||
| 779 | struct iommu_hwpt_page_response { | ||
| 780 | __u32 cookie; | ||
| 781 | __u32 code; | ||
| 782 | }; | ||
| 783 | |||
| 784 | /** | ||
| 785 | * struct iommu_fault_alloc - ioctl(IOMMU_FAULT_QUEUE_ALLOC) | ||
| 786 | * @size: sizeof(struct iommu_fault_alloc) | ||
| 787 | * @flags: Must be 0 | ||
| 788 | * @out_fault_id: The ID of the new FAULT | ||
| 789 | * @out_fault_fd: The fd of the new FAULT | ||
| 790 | * | ||
| 791 | * Explicitly allocate a fault handling object. | ||
| 792 | */ | ||
| 793 | struct iommu_fault_alloc { | ||
| 794 | __u32 size; | ||
| 795 | __u32 flags; | ||
| 796 | __u32 out_fault_id; | ||
| 797 | __u32 out_fault_fd; | ||
| 798 | }; | ||
| 799 | #define IOMMU_FAULT_QUEUE_ALLOC _IO(IOMMUFD_TYPE, IOMMUFD_CMD_FAULT_QUEUE_ALLOC) | ||
| 695 | #endif | 800 | #endif |