summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJérôme Glisse <jglisse@redhat.com>2019-01-27 17:34:43 -0500
committerJérôme Glisse <jglisse@redhat.com>2019-01-29 10:48:51 -0500
commitd4b811eeeff18ec66f92a4443a8f3002ee13e92d (patch)
treef669495db16822a6ecd0c2d43920f9290d79bccb
parent401a567696eafb1d4faf7054ab0d7c3a16a5ef06 (diff)
iommu/amd: add resource map function for AMD IOMMU
Add dma map_resource/unmap_resource functions. This is for peer to peer with IOMMU enabled. As this might not work on all platform it is up to the caller to ascertain that this would work. Signed-off-by: Jérôme Glisse <jglisse@redhat.com> Cc: Christoph Hellwig <hch@lst.de> Cc: Joerg Roedel <jroedel@suse.de>
-rw-r--r--drivers/iommu/amd_iommu.c27
1 files changed, 22 insertions, 5 deletions
diff --git a/drivers/iommu/amd_iommu.c b/drivers/iommu/amd_iommu.c
index 87ba23a75b38..6f4fbb274a95 100644
--- a/drivers/iommu/amd_iommu.c
+++ b/drivers/iommu/amd_iommu.c
@@ -2482,12 +2482,10 @@ static void __unmap_single(struct dma_ops_domain *dma_dom,
/*
* The exported map_single function for dma_ops.
*/
-static dma_addr_t map_page(struct device *dev, struct page *page,
- unsigned long offset, size_t size,
- enum dma_data_direction dir,
- unsigned long attrs)
+static dma_addr_t map_resource(struct device *dev, phys_addr_t paddr,
+ size_t size, enum dma_data_direction dir,
+ unsigned long attrs)
{
- phys_addr_t paddr = page_to_phys(page) + offset;
struct protection_domain *domain;
struct dma_ops_domain *dma_dom;
u64 dma_mask;
@@ -2504,6 +2502,16 @@ static dma_addr_t map_page(struct device *dev, struct page *page,
return __map_single(dev, dma_dom, paddr, size, dir, dma_mask);
}
+static dma_addr_t map_page(struct device *dev, struct page *page,
+ unsigned long offset, size_t size,
+ enum dma_data_direction dir,
+ unsigned long attrs)
+{
+ phys_addr_t paddr = page_to_phys(page) + offset;
+
+ return map_resource(dev, paddr, size, dir, attrs);
+}
+
/*
* The exported unmap_single function for dma_ops.
*/
@@ -2522,6 +2530,13 @@ static void unmap_page(struct device *dev, dma_addr_t dma_addr, size_t size,
__unmap_single(dma_dom, dma_addr, size, dir);
}
+static void unmap_resource(struct device *dev, dma_addr_t dma_addr,
+ size_t size, enum dma_data_direction dir,
+ unsigned long attrs)
+{
+ unmap_page(dev, dma_addr, size, dir, attrs);
+}
+
static int sg_num_pages(struct device *dev,
struct scatterlist *sglist,
int nelems)
@@ -2755,6 +2770,8 @@ static const struct dma_map_ops amd_iommu_dma_ops = {
.map_sg = map_sg,
.unmap_sg = unmap_sg,
.dma_supported = amd_iommu_dma_supported,
+ .map_resource = map_resource,
+ .unmap_resource = unmap_resource,
};
static int init_reserved_iova_ranges(void)