intel_iommu_accel: Handle PASID entry removal for system reset
When system level reset, DMA translation is turned off, all PASID entries become stale and should be deleted. vtd_hiod list is never accessed without BQL, so no need to guard with iommu lock. Signed-off-by: Zhenzhong Duan <zhenzhong.duan@intel.com> Reviewed-by: Yi Liu <yi.l.liu@intel.com> Tested-by: Xudong Hao <xudong.hao@intel.com> Reviewed-by: Michael S. Tsirkin <mst@redhat.com> Signed-off-by: Michael S. Tsirkin <mst@redhat.com> Message-Id: <20260527054658.1021096-15-zhenzhong.duan@intel.com>
Zhenzhong Duan committed
May 27, 2026 at 01:46 UTC
b583cdbb0ebd62d9e2fe678f4620a2827d159038
3 files changed
+20
hw/i386/intel_iommu.c
+2
@@ -391,6 +391,8 @@ static void vtd_reset_caches(IntelIOMMUState *s)
391
vtd_reset_context_cache_locked(s);
392
vtd_pasid_cache_reset_locked(s);
393
vtd_iommu_unlock(s);
394
+
395
+ vtd_accel_pasid_cache_reset(s);
396
}
397
398
static uint64_t vtd_get_iotlb_gfn(hwaddr addr, uint32_t level)
hw/i386/intel_iommu_accel.c
+13
@@ -486,6 +486,19 @@ void vtd_accel_pasid_cache_sync(IntelIOMMUState *s, VTDPASIDCacheInfo *pc_info)
486
}
487
}
488
489
+/* Fake a global pasid cache invalidation to remove all pasid cache entries */
490
+void vtd_accel_pasid_cache_reset(IntelIOMMUState *s)
491
+{
492
+ VTDPASIDCacheInfo pc_info = { .type = VTD_INV_DESC_PASIDC_G_GLOBAL };
493
+ VTDHostIOMMUDevice *vtd_hiod;
494
+ GHashTableIter hiod_it;
495
+
496
+ g_hash_table_iter_init(&hiod_it, s->vtd_host_iommu_dev);
497
+ while (g_hash_table_iter_next(&hiod_it, NULL, (void **)&vtd_hiod)) {
498
+ vtd_accel_pasid_cache_invalidate(vtd_hiod, &pc_info);
499
+ }
500
+}
501
+
502
static uint64_t vtd_get_host_iommu_quirks(uint32_t type,
503
void *caps, uint32_t size)
504
{
hw/i386/intel_iommu_accel.h
+5
@@ -28,6 +28,7 @@ void vtd_flush_host_piotlb_all_locked(IntelIOMMUState *s, uint16_t domain_id,
28
uint32_t pasid, hwaddr addr,
29
uint64_t npages, bool ih);
30
void vtd_accel_pasid_cache_sync(IntelIOMMUState *s, VTDPASIDCacheInfo *pc_info);
31
+void vtd_accel_pasid_cache_reset(IntelIOMMUState *s);
32
void vtd_iommu_ops_update_accel(PCIIOMMUOps *ops);
33
#else
34
static inline bool vtd_check_hiod_accel(IntelIOMMUState *s,
@@ -62,6 +63,10 @@ static inline void vtd_accel_pasid_cache_sync(IntelIOMMUState *s,
63
{
64
}
65
66
+static inline void vtd_accel_pasid_cache_reset(IntelIOMMUState *s)
67
+{
68
+}
69
+
70
static inline void vtd_iommu_ops_update_accel(PCIIOMMUOps *ops)
71
{
72
}