From: Mitchel Humpherys <mitchelh-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
To: linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r@public.gmane.org,
iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA@public.gmane.org,
Will Deacon <will.deacon-5wv7dgnIgG8@public.gmane.org>,
devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
Subject: [PATCH 6/6] iommu/arm-smmu: add .domain_{set, get}_attr for coherent walk control
Date: Tue, 12 Aug 2014 17:51:39 -0700 [thread overview]
Message-ID: <1407891099-24641-7-git-send-email-mitchelh@codeaurora.org> (raw)
In-Reply-To: <1407891099-24641-1-git-send-email-mitchelh-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
Under certain conditions coherent hardware translation table walks can
result in degraded performance. Add a new domain attribute to
disable/enable this feature in generic code along with the domain
attribute setter and getter to handle it in the ARM SMMU driver.
Signed-off-by: Mitchel Humpherys <mitchelh-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
---
drivers/iommu/arm-smmu.c | 57 +++++++++++++++++++++++++++++++-----------------
include/linux/iommu.h | 1 +
2 files changed, 38 insertions(+), 20 deletions(-)
diff --git a/drivers/iommu/arm-smmu.c b/drivers/iommu/arm-smmu.c
index 73d056668b..11672a8371 100644
--- a/drivers/iommu/arm-smmu.c
+++ b/drivers/iommu/arm-smmu.c
@@ -426,6 +426,7 @@ struct arm_smmu_cfg {
u8 irptndx;
u32 cbar;
pgd_t *pgd;
+ bool htw_disable;
};
#define INVALID_IRPTNDX 0xff
@@ -833,14 +834,17 @@ static irqreturn_t arm_smmu_global_fault(int irq, void *dev)
return IRQ_HANDLED;
}
-static void arm_smmu_flush_pgtable(struct arm_smmu_device *smmu, void *addr,
- size_t size)
+static void arm_smmu_flush_pgtable(struct arm_smmu_domain *smmu_domain,
+ void *addr, size_t size)
{
+ struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
+ struct arm_smmu_device *smmu = smmu_domain->smmu;
unsigned long offset = (unsigned long)addr & ~PAGE_MASK;
/* Ensure new page tables are visible to the hardware walker */
- if (smmu->features & ARM_SMMU_FEAT_COHERENT_WALK) {
+ if ((smmu->features & ARM_SMMU_FEAT_COHERENT_WALK) &&
+ !cfg->htw_disable) {
dsb(ishst);
} else {
/*
@@ -943,7 +947,7 @@ static void arm_smmu_init_context_bank(struct arm_smmu_domain *smmu_domain)
}
/* TTBR0 */
- arm_smmu_flush_pgtable(smmu, cfg->pgd,
+ arm_smmu_flush_pgtable(smmu_domain, cfg->pgd,
PTRS_PER_PGD * sizeof(pgd_t));
reg = __pa(cfg->pgd);
writel_relaxed(reg, cb_base + ARM_SMMU_CB_TTBR0_LO);
@@ -1468,7 +1472,8 @@ static bool arm_smmu_pte_is_contiguous_range(unsigned long addr,
(addr + ARM_SMMU_PTE_CONT_SIZE <= end);
}
-static int arm_smmu_alloc_init_pte(struct arm_smmu_device *smmu, pmd_t *pmd,
+static int arm_smmu_alloc_init_pte(struct arm_smmu_domain *smmu_domain,
+ pmd_t *pmd,
unsigned long addr, unsigned long end,
unsigned long pfn, int prot, int stage)
{
@@ -1482,9 +1487,10 @@ static int arm_smmu_alloc_init_pte(struct arm_smmu_device *smmu, pmd_t *pmd,
if (!table)
return -ENOMEM;
- arm_smmu_flush_pgtable(smmu, page_address(table), PAGE_SIZE);
+ arm_smmu_flush_pgtable(smmu_domain, page_address(table),
+ PAGE_SIZE);
pmd_populate(NULL, pmd, table);
- arm_smmu_flush_pgtable(smmu, pmd, sizeof(*pmd));
+ arm_smmu_flush_pgtable(smmu_domain, pmd, sizeof(*pmd));
}
if (stage == 1) {
@@ -1558,7 +1564,7 @@ static int arm_smmu_alloc_init_pte(struct arm_smmu_device *smmu, pmd_t *pmd,
pte_val(*(cont_start + j)) &=
~ARM_SMMU_PTE_CONT;
- arm_smmu_flush_pgtable(smmu, cont_start,
+ arm_smmu_flush_pgtable(smmu_domain, cont_start,
sizeof(*pte) *
ARM_SMMU_PTE_CONT_ENTRIES);
}
@@ -1568,11 +1574,13 @@ static int arm_smmu_alloc_init_pte(struct arm_smmu_device *smmu, pmd_t *pmd,
} while (pte++, pfn++, addr += PAGE_SIZE, --i);
} while (addr != end);
- arm_smmu_flush_pgtable(smmu, start, sizeof(*pte) * (pte - start));
+ arm_smmu_flush_pgtable(smmu_domain, start,
+ sizeof(*pte) * (pte - start));
return 0;
}
-static int arm_smmu_alloc_init_pmd(struct arm_smmu_device *smmu, pud_t *pud,
+static int arm_smmu_alloc_init_pmd(struct arm_smmu_domain *smmu_domain,
+ pud_t *pud,
unsigned long addr, unsigned long end,
phys_addr_t phys, int prot, int stage)
{
@@ -1586,9 +1594,9 @@ static int arm_smmu_alloc_init_pmd(struct arm_smmu_device *smmu, pud_t *pud,
if (!pmd)
return -ENOMEM;
- arm_smmu_flush_pgtable(smmu, pmd, PAGE_SIZE);
+ arm_smmu_flush_pgtable(smmu_domain, pmd, PAGE_SIZE);
pud_populate(NULL, pud, pmd);
- arm_smmu_flush_pgtable(smmu, pud, sizeof(*pud));
+ arm_smmu_flush_pgtable(smmu_domain, pud, sizeof(*pud));
pmd += pmd_index(addr);
} else
@@ -1597,7 +1605,7 @@ static int arm_smmu_alloc_init_pmd(struct arm_smmu_device *smmu, pud_t *pud,
do {
next = pmd_addr_end(addr, end);
- ret = arm_smmu_alloc_init_pte(smmu, pmd, addr, next, pfn,
+ ret = arm_smmu_alloc_init_pte(smmu_domain, pmd, addr, next, pfn,
prot, stage);
phys += next - addr;
} while (pmd++, addr = next, addr < end);
@@ -1605,7 +1613,8 @@ static int arm_smmu_alloc_init_pmd(struct arm_smmu_device *smmu, pud_t *pud,
return ret;
}
-static int arm_smmu_alloc_init_pud(struct arm_smmu_device *smmu, pgd_t *pgd,
+static int arm_smmu_alloc_init_pud(struct arm_smmu_domain *smmu_domain,
+ pgd_t *pgd,
unsigned long addr, unsigned long end,
phys_addr_t phys, int prot, int stage)
{
@@ -1619,9 +1628,9 @@ static int arm_smmu_alloc_init_pud(struct arm_smmu_device *smmu, pgd_t *pgd,
if (!pud)
return -ENOMEM;
- arm_smmu_flush_pgtable(smmu, pud, PAGE_SIZE);
+ arm_smmu_flush_pgtable(smmu_domain, pud, PAGE_SIZE);
pgd_populate(NULL, pgd, pud);
- arm_smmu_flush_pgtable(smmu, pgd, sizeof(*pgd));
+ arm_smmu_flush_pgtable(smmu_domain, pgd, sizeof(*pgd));
pud += pud_index(addr);
} else
@@ -1630,8 +1639,8 @@ static int arm_smmu_alloc_init_pud(struct arm_smmu_device *smmu, pgd_t *pgd,
do {
next = pud_addr_end(addr, end);
- ret = arm_smmu_alloc_init_pmd(smmu, pud, addr, next, phys,
- prot, stage);
+ ret = arm_smmu_alloc_init_pmd(smmu_domain, pud, addr, next,
+ phys, prot, stage);
phys += next - addr;
} while (pud++, addr = next, addr < end);
@@ -1677,8 +1686,8 @@ static int arm_smmu_handle_mapping(struct arm_smmu_domain *smmu_domain,
do {
unsigned long next = pgd_addr_end(iova, end);
- ret = arm_smmu_alloc_init_pud(smmu, pgd, iova, next, paddr,
- prot, stage);
+ ret = arm_smmu_alloc_init_pud(smmu_domain, pgd, iova, next,
+ paddr, prot, stage);
if (ret)
goto out_unlock;
@@ -1908,11 +1917,15 @@ static int arm_smmu_domain_get_attr(struct iommu_domain *domain,
enum iommu_attr attr, void *data)
{
struct arm_smmu_domain *smmu_domain = domain->priv;
+ struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
switch (attr) {
case DOMAIN_ATTR_NESTING:
*(int *)data = (smmu_domain->stage == ARM_SMMU_DOMAIN_NESTED);
return 0;
+ case DOMAIN_ATTR_COHERENT_HTW_DISABLE:
+ *((bool *)data) = cfg->htw_disable;
+ return 0;
default:
return -ENODEV;
}
@@ -1922,6 +1935,7 @@ static int arm_smmu_domain_set_attr(struct iommu_domain *domain,
enum iommu_attr attr, void *data)
{
struct arm_smmu_domain *smmu_domain = domain->priv;
+ struct arm_smmu_cfg *cfg = &smmu_domain->cfg;
switch (attr) {
case DOMAIN_ATTR_NESTING:
@@ -1933,6 +1947,9 @@ static int arm_smmu_domain_set_attr(struct iommu_domain *domain,
smmu_domain->stage = ARM_SMMU_DOMAIN_S1;
return 0;
+ case DOMAIN_ATTR_COHERENT_HTW_DISABLE:
+ cfg->htw_disable = *((bool *)data);
+ return 0;
default:
return -ENODEV;
}
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index 0550286df4..8a6449857a 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -81,6 +81,7 @@ enum iommu_attr {
DOMAIN_ATTR_FSL_PAMU_ENABLE,
DOMAIN_ATTR_FSL_PAMUV1,
DOMAIN_ATTR_NESTING, /* two stages of translation */
+ DOMAIN_ATTR_COHERENT_HTW_DISABLE,
DOMAIN_ATTR_MAX,
};
--
The Qualcomm Innovation Center, Inc. is a member of the Code Aurora Forum,
hosted by The Linux Foundation
next prev parent reply other threads:[~2014-08-13 0:51 UTC|newest]
Thread overview: 34+ messages / expand[flat|nested] mbox.gz Atom feed top
2014-08-13 0:51 [PATCH 0/6] iommu/arm-smmu: misc features, new DT bindings Mitchel Humpherys
[not found] ` <1407891099-24641-1-git-send-email-mitchelh-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
2014-08-13 0:51 ` [PATCH 1/6] iommu/arm-smmu: add support for specifying clocks Mitchel Humpherys
[not found] ` <1407891099-24641-2-git-send-email-mitchelh-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
2014-08-13 21:07 ` Mitchel Humpherys
2014-08-19 12:58 ` Will Deacon
[not found] ` <20140819125833.GO23128-5wv7dgnIgG8@public.gmane.org>
2014-08-19 19:03 ` Olav Haugan
[not found] ` <53F39F6D.1040205-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
2014-08-26 14:27 ` Will Deacon
[not found] ` <20140826142757.GU23445-5wv7dgnIgG8@public.gmane.org>
2014-09-10 1:29 ` Mitchel Humpherys
[not found] ` <vnkwa968b6ux.fsf-Yf+dfxj6toJBVvN7MMdr1KRtKmQZhJ7pQQ4Iyu8u01E@public.gmane.org>
2014-09-10 18:27 ` Will Deacon
[not found] ` <20140910182739.GM1710-5wv7dgnIgG8@public.gmane.org>
2014-09-10 19:09 ` Mitchel Humpherys
[not found] ` <vnkwbnqn9tt9.fsf-Yf+dfxj6toJBVvN7MMdr1KRtKmQZhJ7pQQ4Iyu8u01E@public.gmane.org>
2014-09-15 18:38 ` Mitchel Humpherys
2014-08-19 19:28 ` Mitchel Humpherys
2014-08-13 0:51 ` [PATCH 2/6] iommu/arm-smmu: add support for specifying regulators Mitchel Humpherys
[not found] ` <1407891099-24641-3-git-send-email-mitchelh-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
2014-08-13 21:17 ` Mitchel Humpherys
2014-08-19 13:00 ` Will Deacon
2014-08-13 0:51 ` [PATCH 3/6] iommu/arm-smmu: add support for iova_to_phys through ATS1PR Mitchel Humpherys
[not found] ` <1407891099-24641-4-git-send-email-mitchelh-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
2014-08-19 12:44 ` Will Deacon
[not found] ` <20140819124431.GL23128-5wv7dgnIgG8@public.gmane.org>
2014-08-19 18:12 ` Mitchel Humpherys
[not found] ` <vnkwa970qrfq.fsf-Yf+dfxj6toJBVvN7MMdr1KRtKmQZhJ7pQQ4Iyu8u01E@public.gmane.org>
2014-08-26 13:54 ` Will Deacon
[not found] ` <20140826135451.GQ23445-5wv7dgnIgG8@public.gmane.org>
2014-09-01 16:15 ` Will Deacon
2014-08-13 0:51 ` [PATCH 4/6] iommu/arm-smmu: implement generic DT bindings Mitchel Humpherys
[not found] ` <1407891099-24641-5-git-send-email-mitchelh-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
2014-08-13 16:53 ` Mitchel Humpherys
2014-08-19 12:54 ` Will Deacon
[not found] ` <20140819125449.GN23128-5wv7dgnIgG8@public.gmane.org>
2014-08-19 15:54 ` Hiroshi Doyu
2014-08-20 3:18 ` Arnd Bergmann
2014-08-13 0:51 ` [PATCH 5/6] iommu/arm-smmu: support buggy implementations with invalidate-on-map Mitchel Humpherys
[not found] ` <1407891099-24641-6-git-send-email-mitchelh-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
2014-11-12 18:26 ` Will Deacon
[not found] ` <20141112182642.GH26437-5wv7dgnIgG8@public.gmane.org>
2014-11-12 18:58 ` Mitchel Humpherys
[not found] ` <vnkwy4rg5jqu.fsf-Yf+dfxj6toJBVvN7MMdr1KRtKmQZhJ7pQQ4Iyu8u01E@public.gmane.org>
2014-11-13 9:48 ` Will Deacon
[not found] ` <20141113094826.GA13350-5wv7dgnIgG8@public.gmane.org>
2014-11-14 23:08 ` Mitchel Humpherys
2014-08-13 0:51 ` Mitchel Humpherys [this message]
[not found] ` <1407891099-24641-7-git-send-email-mitchelh-sgV2jX0FEOL9JmXXK+q4OQ@public.gmane.org>
2014-08-19 12:48 ` [PATCH 6/6] iommu/arm-smmu: add .domain_{set,get}_attr for coherent walk control Will Deacon
[not found] ` <20140819124807.GM23128-5wv7dgnIgG8@public.gmane.org>
2014-08-19 19:19 ` [PATCH 6/6] iommu/arm-smmu: add .domain_{set, get}_attr " Mitchel Humpherys
2014-08-13 17:22 ` [PATCH 0/6] iommu/arm-smmu: misc features, new DT bindings Mitchel Humpherys
[not found] ` <vnkwvbpwl2xz.fsf-Yf+dfxj6toJBVvN7MMdr1KRtKmQZhJ7pQQ4Iyu8u01E@public.gmane.org>
2014-08-15 17:25 ` Will Deacon
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=1407891099-24641-7-git-send-email-mitchelh@codeaurora.org \
--to=mitchelh-sgv2jx0feol9jmxxk+q4oq@public.gmane.org \
--cc=devicetree-u79uwXL29TY76Z2rM5mHXA@public.gmane.org \
--cc=iommu-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA@public.gmane.org \
--cc=linux-arm-kernel-IAPFreCvJWM7uuMidbF8XUB+6BGkLq7r@public.gmane.org \
--cc=will.deacon-5wv7dgnIgG8@public.gmane.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).