linux-arm-kernel.lists.infradead.org archive mirror
 help / color / mirror / Atom feed
From: eric.auger@redhat.com (Eric Auger)
To: linux-arm-kernel@lists.infradead.org
Subject: [PATCH v7 01/19] iommu/dma: Implement PCI allocation optimisation
Date: Mon,  9 Jan 2017 13:45:52 +0000	[thread overview]
Message-ID: <1483969570-3154-2-git-send-email-eric.auger@redhat.com> (raw)
In-Reply-To: <1483969570-3154-1-git-send-email-eric.auger@redhat.com>

From: Robin Murphy <robin.murphy@arm.com>

Whilst PCI devices may have 64-bit DMA masks, they still benefit from
using 32-bit addresses wherever possible in order to avoid DAC (PCI) or
longer address packets (PCIe), which may incur a performance overhead.
Implement the same optimisation as other allocators by trying to get a
32-bit address first, only falling back to the full mask if that fails.

Signed-off-by: Robin Murphy <robin.murphy@arm.com>
---
 drivers/iommu/dma-iommu.c | 21 +++++++++++++++------
 1 file changed, 15 insertions(+), 6 deletions(-)

diff --git a/drivers/iommu/dma-iommu.c b/drivers/iommu/dma-iommu.c
index 2db0d64..a59ca47 100644
--- a/drivers/iommu/dma-iommu.c
+++ b/drivers/iommu/dma-iommu.c
@@ -204,19 +204,28 @@ int dma_direction_to_prot(enum dma_data_direction dir, bool coherent)
 }
 
 static struct iova *__alloc_iova(struct iommu_domain *domain, size_t size,
-		dma_addr_t dma_limit)
+		dma_addr_t dma_limit, struct device *dev)
 {
 	struct iova_domain *iovad = cookie_iovad(domain);
 	unsigned long shift = iova_shift(iovad);
 	unsigned long length = iova_align(iovad, size) >> shift;
+	struct iova *iova = NULL;
 
 	if (domain->geometry.force_aperture)
 		dma_limit = min(dma_limit, domain->geometry.aperture_end);
+
+	/* Try to get PCI devices a SAC address */
+	if (dma_limit > DMA_BIT_MASK(32) && dev_is_pci(dev))
+		iova = alloc_iova(iovad, length, DMA_BIT_MASK(32) >> shift,
+				  true);
 	/*
 	 * Enforce size-alignment to be safe - there could perhaps be an
 	 * attribute to control this per-device, or at least per-domain...
 	 */
-	return alloc_iova(iovad, length, dma_limit >> shift, true);
+	if (!iova)
+		iova = alloc_iova(iovad, length, dma_limit >> shift, true);
+
+	return iova;
 }
 
 /* The IOVA allocator knows what we mapped, so just unmap whatever that was */
@@ -369,7 +378,7 @@ struct page **iommu_dma_alloc(struct device *dev, size_t size, gfp_t gfp,
 	if (!pages)
 		return NULL;
 
-	iova = __alloc_iova(domain, size, dev->coherent_dma_mask);
+	iova = __alloc_iova(domain, size, dev->coherent_dma_mask, dev);
 	if (!iova)
 		goto out_free_pages;
 
@@ -440,7 +449,7 @@ static dma_addr_t __iommu_dma_map(struct device *dev, phys_addr_t phys,
 	struct iova_domain *iovad = cookie_iovad(domain);
 	size_t iova_off = iova_offset(iovad, phys);
 	size_t len = iova_align(iovad, size + iova_off);
-	struct iova *iova = __alloc_iova(domain, len, dma_get_mask(dev));
+	struct iova *iova = __alloc_iova(domain, len, dma_get_mask(dev), dev);
 
 	if (!iova)
 		return DMA_ERROR_CODE;
@@ -598,7 +607,7 @@ int iommu_dma_map_sg(struct device *dev, struct scatterlist *sg,
 		prev = s;
 	}
 
-	iova = __alloc_iova(domain, iova_len, dma_get_mask(dev));
+	iova = __alloc_iova(domain, iova_len, dma_get_mask(dev), dev);
 	if (!iova)
 		goto out_restore_sg;
 
@@ -675,7 +684,7 @@ static struct iommu_dma_msi_page *iommu_dma_get_msi_page(struct device *dev,
 	if (!msi_page)
 		return NULL;
 
-	iova = __alloc_iova(domain, iovad->granule, dma_get_mask(dev));
+	iova = __alloc_iova(domain, iovad->granule, dma_get_mask(dev), dev);
 	if (!iova)
 		goto out_free_page;
 
-- 
1.9.1

  reply	other threads:[~2017-01-09 13:45 UTC|newest]

Thread overview: 33+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2017-01-09 13:45 [PATCH v7 00/19] KVM PCIe/MSI passthrough on ARM/ARM64 and IOVA reserved regions Eric Auger
2017-01-09 13:45 ` Eric Auger [this message]
2017-01-10 15:41   ` [PATCH v7 01/19] iommu/dma: Implement PCI allocation optimisation Robin Murphy
2017-01-09 13:45 ` [PATCH v7 02/19] iommu/dma: Allow MSI-only cookies Eric Auger
2017-01-09 13:45 ` [PATCH v7 03/19] iommu: Rename iommu_dm_regions into iommu_resv_regions Eric Auger
2017-01-09 13:45 ` [PATCH v7 04/19] iommu: Add a new type field in iommu_resv_region Eric Auger
2017-01-09 13:45 ` [PATCH v7 05/19] iommu: iommu_alloc_resv_region Eric Auger
2017-01-09 13:45 ` [PATCH v7 06/19] iommu: Only map direct mapped regions Eric Auger
2017-01-09 13:45 ` [PATCH v7 07/19] iommu: iommu_get_group_resv_regions Eric Auger
2017-01-09 13:45 ` [PATCH v7 08/19] iommu: Implement reserved_regions iommu-group sysfs file Eric Auger
2017-01-10 16:20   ` Auger Eric
2017-01-10 17:14     ` Joerg Roedel
2017-01-10 21:21       ` Auger Eric
2017-01-09 13:46 ` [PATCH v7 09/19] iommu/vt-d: Implement reserved region get/put callbacks Eric Auger
2017-01-09 13:46 ` [PATCH v7 10/19] iommu/amd: Declare MSI and HT regions as reserved IOVA regions Eric Auger
2017-01-09 13:46 ` [PATCH v7 11/19] iommu/arm-smmu: Implement reserved region get/put callbacks Eric Auger
2017-01-10 14:16   ` Will Deacon
2017-01-09 13:46 ` [PATCH v7 12/19] iommu/arm-smmu-v3: " Eric Auger
2017-01-10 14:17   ` Will Deacon
2017-01-09 13:46 ` [PATCH v7 13/19] irqdomain: Add irq domain MSI and MSI_REMAP flags Eric Auger
2017-01-10 11:50   ` Marc Zyngier
2017-01-09 13:46 ` [PATCH v7 14/19] genirq/msi: Set IRQ_DOMAIN_FLAG_MSI on MSI domain creation Eric Auger
2017-01-09 13:46 ` [PATCH v7 15/19] irqdomain: irq_domain_check_msi_remap Eric Auger
2017-01-10 11:54   ` Marc Zyngier
2017-01-09 13:46 ` [PATCH v7 16/19] irqchip/gicv3-its: Sets IRQ_DOMAIN_FLAG_MSI_REMAP Eric Auger
2017-01-10 11:57   ` Marc Zyngier
2017-01-09 13:46 ` [PATCH v7 17/19] vfio/type1: Allow transparent MSI IOVA allocation Eric Auger
2017-01-09 13:46 ` [PATCH v7 18/19] vfio/type1: Check MSI remapping at irq domain level Eric Auger
2017-01-09 13:46 ` [PATCH v7 19/19] iommu/arm-smmu: Do not advertise IOMMU_CAP_INTR_REMAP anymore Eric Auger
2017-01-10 14:17   ` Will Deacon
2017-01-10 14:09 ` [PATCH v7 00/19] KVM PCIe/MSI passthrough on ARM/ARM64 and IOVA reserved regions Joerg Roedel
2017-01-10 14:15   ` Will Deacon
2017-01-10 15:58   ` Auger Eric

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1483969570-3154-2-git-send-email-eric.auger@redhat.com \
    --to=eric.auger@redhat.com \
    --cc=linux-arm-kernel@lists.infradead.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).