summaryrefslogtreecommitdiff
path: root/arch/xtensa/mm/highmem.c
diff options
context:
space:
mode:
authorMax Filippov <jcmvbkbc@gmail.com>2014-07-15 02:51:49 +0400
committerMax Filippov <jcmvbkbc@gmail.com>2014-08-14 11:59:21 +0400
commit32544d9c10c42bac3be8b87d2fc95b0aef008795 (patch)
tree11983adf6b934cc71ba3013623d8869c867b49fd /arch/xtensa/mm/highmem.c
parenta91902db2990909ea5e6b110811b448f2e8f1571 (diff)
xtensa: support aliasing cache in k[un]map_atomic
Map high memory pages at virtual addresses with color that match color of their physical address. Existing cache alias management mechanisms may be used with such pages. Signed-off-by: Max Filippov <jcmvbkbc@gmail.com>
Diffstat (limited to 'arch/xtensa/mm/highmem.c')
-rw-r--r--arch/xtensa/mm/highmem.c17
1 files changed, 10 insertions, 7 deletions
diff --git a/arch/xtensa/mm/highmem.c b/arch/xtensa/mm/highmem.c
index 2e95a7665bf3..466abaed5382 100644
--- a/arch/xtensa/mm/highmem.c
+++ b/arch/xtensa/mm/highmem.c
@@ -14,18 +14,23 @@
static pte_t *kmap_pte;
+static inline enum fixed_addresses kmap_idx(int type, unsigned long color)
+{
+ return (type + KM_TYPE_NR * smp_processor_id()) * DCACHE_N_COLORS +
+ color;
+}
+
void *kmap_atomic(struct page *page)
{
enum fixed_addresses idx;
unsigned long vaddr;
- int type;
pagefault_disable();
if (!PageHighMem(page))
return page_address(page);
- type = kmap_atomic_idx_push();
- idx = type + KM_TYPE_NR * smp_processor_id();
+ idx = kmap_idx(kmap_atomic_idx_push(),
+ DCACHE_ALIAS(page_to_phys(page)));
vaddr = __fix_to_virt(FIX_KMAP_BEGIN + idx);
#ifdef CONFIG_DEBUG_HIGHMEM
BUG_ON(!pte_none(*(kmap_pte + idx)));
@@ -38,12 +43,10 @@ EXPORT_SYMBOL(kmap_atomic);
void __kunmap_atomic(void *kvaddr)
{
- int idx, type;
-
if (kvaddr >= (void *)FIXADDR_START &&
kvaddr < (void *)FIXADDR_TOP) {
- type = kmap_atomic_idx();
- idx = type + KM_TYPE_NR * smp_processor_id();
+ int idx = kmap_idx(kmap_atomic_idx(),
+ DCACHE_ALIAS((unsigned long)kvaddr));
/*
* Force other mappings to Oops if they'll try to access this