[lkml]   [2009]   [Sep]   [16]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
Messages in this thread
Patch in this message
Subject[patch 31/45] ARM: 5691/1: fix cache aliasing issues between kmap() and kmap_atomic() with highmem
2.6.31-stable review patch.  If anyone has any objections, please let us know.

From: Nicolas Pitre <>

commit 7929eb9cf643ae416e5081b2a6fa558d37b9854c upstream.

Let's suppose a highmem page is kmap'd with kmap(). A pkmap entry is
used, the page mapped to it, and the virtual cache is dirtied. Then
kunmap() is used which does virtually nothing except for decrementing a
usage count.

Then, let's suppose the _same_ page gets mapped using kmap_atomic().
It is therefore mapped onto a fixmap entry instead, which has a
different virtual address unaware of the dirty cache data for that page
sitting in the pkmap mapping.

Fortunately it is easy to know if a pkmap mapping still exists for that
page and use it directly with kmap_atomic(), thanks to kmap_high_get().

And actual testing with a printk in the added code path shows that this
condition is actually met *extremely* frequently. Seems that we've been
quite lucky that things have worked so well with highmem so far.

Signed-off-by: Nicolas Pitre <>
Signed-off-by: Russell King <>
Signed-off-by: Greg Kroah-Hartman <>

--- a/arch/arm/mm/highmem.c
+++ b/arch/arm/mm/highmem.c
@@ -40,11 +40,16 @@ void *kmap_atomic(struct page *page, enum km_type type)
unsigned int idx;
unsigned long vaddr;
+ void *kmap;

if (!PageHighMem(page))
return page_address(page);

+ kmap = kmap_high_get(page);
+ if (kmap)
+ return kmap;
idx = type + KM_TYPE_NR * smp_processor_id();
vaddr = __fix_to_virt(FIX_KMAP_BEGIN + idx);
@@ -80,6 +85,9 @@ void kunmap_atomic(void *kvaddr, enum km_type type)
(void) idx; /* to kill a warning */
+ } else if (vaddr >= PKMAP_ADDR(0) && vaddr < PKMAP_ADDR(LAST_PKMAP)) {
+ /* this address was obtained through kmap_high_get() */
+ kunmap_high(pte_page(pkmap_page_table[PKMAP_NR(vaddr)]));

 \ /
  Last update: 2009-09-17 01:15    [W:0.153 / U:4.652 seconds]
©2003-2018 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site