From: Robin Murphy <robin.murphy@arm.com>
To: joro@8bytes.org
Cc: iommu@lists.linux-foundation.org, thunder.leizhen@huawei.com,
nwatters@codeaurora.org, tomasz.nowicki@caviumnetworks.com,
dwoods@mellanox.com, linux-kernel@vger.kernel.org
Subject: [PATCH v5 5/6] iommu/iova: Add rbtree anchor node
Date: Thu, 21 Sep 2017 16:52:46 +0100 [thread overview]
Message-ID: <2d78b05d4fa2beed3fe7f1b4e91370d982a29aac.1506007392.git.robin.murphy@arm.com> (raw)
In-Reply-To: <cover.1506007392.git.robin.murphy@arm.com>
Add a permanent dummy IOVA reservation to the rbtree, such that we can
always access the top of the address space instantly. The immediate
benefit is that we remove the overhead of the rb_last() traversal when
not using the cached node, but it also paves the way for further
simplifications.
Signed-off-by: Robin Murphy <robin.murphy@arm.com>
---
v5: No change
drivers/iommu/iova.c | 15 +++++++++++++--
include/linux/iova.h | 1 +
2 files changed, 14 insertions(+), 2 deletions(-)
diff --git a/drivers/iommu/iova.c b/drivers/iommu/iova.c
index 65032e60a5d1..9e04c1f3e740 100644
--- a/drivers/iommu/iova.c
+++ b/drivers/iommu/iova.c
@@ -24,6 +24,9 @@
#include <linux/bitops.h>
#include <linux/cpu.h>
+/* The anchor node sits above the top of the usable address space */
+#define IOVA_ANCHOR ~0UL
+
static bool iova_rcache_insert(struct iova_domain *iovad,
unsigned long pfn,
unsigned long size);
@@ -55,6 +58,9 @@ init_iova_domain(struct iova_domain *iovad, unsigned long granule,
iovad->dma_32bit_pfn = 1UL << (32 - iova_shift(iovad));
iovad->flush_cb = NULL;
iovad->fq = NULL;
+ iovad->anchor.pfn_lo = iovad->anchor.pfn_hi = IOVA_ANCHOR;
+ rb_link_node(&iovad->anchor.node, NULL, &iovad->rbroot.rb_node);
+ rb_insert_color(&iovad->anchor.node, &iovad->rbroot);
init_iova_rcaches(iovad);
}
EXPORT_SYMBOL_GPL(init_iova_domain);
@@ -119,7 +125,7 @@ __get_cached_rbnode(struct iova_domain *iovad, unsigned long *limit_pfn)
if (!cached_node)
cached_node = iovad->cached_node;
if (!cached_node)
- return rb_last(&iovad->rbroot);
+ return rb_prev(&iovad->anchor.node);
curr_iova = rb_entry(cached_node, struct iova, node);
*limit_pfn = min(*limit_pfn, curr_iova->pfn_lo);
@@ -242,7 +248,8 @@ EXPORT_SYMBOL(alloc_iova_mem);
void free_iova_mem(struct iova *iova)
{
- kmem_cache_free(iova_cache, iova);
+ if (iova->pfn_lo != IOVA_ANCHOR)
+ kmem_cache_free(iova_cache, iova);
}
EXPORT_SYMBOL(free_iova_mem);
@@ -676,6 +683,10 @@ reserve_iova(struct iova_domain *iovad,
struct iova *iova;
unsigned int overlap = 0;
+ /* Don't allow nonsensical pfns */
+ if (WARN_ON((pfn_hi | pfn_lo) > (ULLONG_MAX >> iova_shift(iovad))))
+ return NULL;
+
spin_lock_irqsave(&iovad->iova_rbtree_lock, flags);
for (node = rb_first(&iovad->rbroot); node; node = rb_next(node)) {
if (__is_range_overlap(node, pfn_lo, pfn_hi)) {
diff --git a/include/linux/iova.h b/include/linux/iova.h
index 953cfd20f152..c696ee81054e 100644
--- a/include/linux/iova.h
+++ b/include/linux/iova.h
@@ -75,6 +75,7 @@ struct iova_domain {
unsigned long granule; /* pfn granularity for this domain */
unsigned long start_pfn; /* Lower limit for this domain */
unsigned long dma_32bit_pfn;
+ struct iova anchor; /* rbtree lookup anchor */
struct iova_rcache rcaches[IOVA_RANGE_CACHE_MAX_SIZE]; /* IOVA range caches */
iova_flush_cb flush_cb; /* Call-Back function to flush IOMMU
--
2.13.4.dirty
next prev parent reply other threads:[~2017-09-21 15:53 UTC|newest]
Thread overview: 12+ messages / expand[flat|nested] mbox.gz Atom feed top
2017-09-21 15:52 [PATCH v5 0/6] Optimise 64-bit IOVA allocations Robin Murphy
2017-09-21 15:52 ` [PATCH v5 1/6] iommu/iova: Optimise rbtree searching Robin Murphy
2017-09-21 15:52 ` [PATCH v5 2/6] iommu/iova: Optimise the padding calculation Robin Murphy
2017-09-21 15:52 ` [PATCH v5 3/6] iommu/iova: Extend rbtree node caching Robin Murphy
2017-09-22 16:21 ` Tomasz Nowicki
2017-09-22 16:50 ` tn
2017-09-22 17:08 ` tn
2017-09-22 17:25 ` Robin Murphy
2017-09-21 15:52 ` [PATCH v5 4/6] iommu/iova: Make dma_32bit_pfn implicit Robin Murphy
2017-09-21 15:52 ` Robin Murphy [this message]
2017-09-21 15:52 ` [PATCH v5 6/6] iommu/iova: Simplify cached node logic Robin Murphy
2017-09-27 15:11 ` [PATCH v5 0/6] Optimise 64-bit IOVA allocations Joerg Roedel
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=2d78b05d4fa2beed3fe7f1b4e91370d982a29aac.1506007392.git.robin.murphy@arm.com \
--to=robin.murphy@arm.com \
--cc=dwoods@mellanox.com \
--cc=iommu@lists.linux-foundation.org \
--cc=joro@8bytes.org \
--cc=linux-kernel@vger.kernel.org \
--cc=nwatters@codeaurora.org \
--cc=thunder.leizhen@huawei.com \
--cc=tomasz.nowicki@caviumnetworks.com \
/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
all inboxes | Powered by JetHome®