diff options
Diffstat (limited to 'drivers/pci/intel-iommu.c')
-rw-r--r-- | drivers/pci/intel-iommu.c | 22 |
1 files changed, 22 insertions, 0 deletions
diff --git a/drivers/pci/intel-iommu.c b/drivers/pci/intel-iommu.c index 9dca689215eb..3ecfa2304c2c 100644 --- a/drivers/pci/intel-iommu.c +++ b/drivers/pci/intel-iommu.c | |||
@@ -362,6 +362,28 @@ void free_iova_mem(struct iova *iova) | |||
362 | kmem_cache_free(iommu_iova_cache, iova); | 362 | kmem_cache_free(iommu_iova_cache, iova); |
363 | } | 363 | } |
364 | 364 | ||
365 | |||
366 | static inline int width_to_agaw(int width); | ||
367 | |||
368 | /* calculate agaw for each iommu. | ||
369 | * "SAGAW" may be different across iommus, use a default agaw, and | ||
370 | * get a supported less agaw for iommus that don't support the default agaw. | ||
371 | */ | ||
372 | int iommu_calculate_agaw(struct intel_iommu *iommu) | ||
373 | { | ||
374 | unsigned long sagaw; | ||
375 | int agaw = -1; | ||
376 | |||
377 | sagaw = cap_sagaw(iommu->cap); | ||
378 | for (agaw = width_to_agaw(DEFAULT_DOMAIN_ADDRESS_WIDTH); | ||
379 | agaw >= 0; agaw--) { | ||
380 | if (test_bit(agaw, &sagaw)) | ||
381 | break; | ||
382 | } | ||
383 | |||
384 | return agaw; | ||
385 | } | ||
386 | |||
365 | /* in native case, each domain is related to only one iommu */ | 387 | /* in native case, each domain is related to only one iommu */ |
366 | static struct intel_iommu *domain_get_iommu(struct dmar_domain *domain) | 388 | static struct intel_iommu *domain_get_iommu(struct dmar_domain *domain) |
367 | { | 389 | { |