diff options
author | Hugh Dickins <hugh@veritas.com> | 2005-10-29 21:16:36 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@g5.osdl.org> | 2005-10-30 00:40:42 -0400 |
commit | 92dc6fcc845d99e87d8168e0786796525832d130 (patch) | |
tree | ac36da7e3dc3e0ba62d4139443beb7eb7c25288d /arch/parisc/kernel/cache.c | |
parent | 69b0475456ff7ef520e16f69d7a15c0d68b74e64 (diff) |
[PATCH] mm: parisc pte atomicity
There's a worrying function translation_exists in parisc cacheflush.h,
unaffected by split ptlock since flush_dcache_page is using it on some other
mm, without any relevant lock. Oh well, make it a slightly more robust by
factoring the pfn check within it. And it looked liable to confuse a
camouflaged swap or file entry with a good pte: fix that too.
Signed-off-by: Hugh Dickins <hugh@veritas.com>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
Diffstat (limited to 'arch/parisc/kernel/cache.c')
-rw-r--r-- | arch/parisc/kernel/cache.c | 24 |
1 files changed, 9 insertions, 15 deletions
diff --git a/arch/parisc/kernel/cache.c b/arch/parisc/kernel/cache.c index e15f09eaed12..a065349aee37 100644 --- a/arch/parisc/kernel/cache.c +++ b/arch/parisc/kernel/cache.c | |||
@@ -270,7 +270,6 @@ void flush_dcache_page(struct page *page) | |||
270 | unsigned long offset; | 270 | unsigned long offset; |
271 | unsigned long addr; | 271 | unsigned long addr; |
272 | pgoff_t pgoff; | 272 | pgoff_t pgoff; |
273 | pte_t *pte; | ||
274 | unsigned long pfn = page_to_pfn(page); | 273 | unsigned long pfn = page_to_pfn(page); |
275 | 274 | ||
276 | 275 | ||
@@ -301,21 +300,16 @@ void flush_dcache_page(struct page *page) | |||
301 | * taking a page fault if the pte doesn't exist. | 300 | * taking a page fault if the pte doesn't exist. |
302 | * This is just for speed. If the page translation | 301 | * This is just for speed. If the page translation |
303 | * isn't there, there's no point exciting the | 302 | * isn't there, there's no point exciting the |
304 | * nadtlb handler into a nullification frenzy */ | 303 | * nadtlb handler into a nullification frenzy. |
305 | 304 | * | |
306 | 305 | * Make sure we really have this page: the private | |
307 | if(!(pte = translation_exists(mpnt, addr))) | ||
308 | continue; | ||
309 | |||
310 | /* make sure we really have this page: the private | ||
311 | * mappings may cover this area but have COW'd this | 306 | * mappings may cover this area but have COW'd this |
312 | * particular page */ | 307 | * particular page. |
313 | if(pte_pfn(*pte) != pfn) | 308 | */ |
314 | continue; | 309 | if (translation_exists(mpnt, addr, pfn)) { |
315 | 310 | __flush_cache_page(mpnt, addr); | |
316 | __flush_cache_page(mpnt, addr); | 311 | break; |
317 | 312 | } | |
318 | break; | ||
319 | } | 313 | } |
320 | flush_dcache_mmap_unlock(mapping); | 314 | flush_dcache_mmap_unlock(mapping); |
321 | } | 315 | } |