forked from luck/tmp_suning_uos_patched
[PATCH] ppc64: Fix huge pages MMU mapping bug
Current kernel has a couple of sneaky bugs in the ppc64 hugetlb code that cause huge pages to be potentially left stale in the hash table and TLBs (improperly invalidated), with all the nasty consequences that can have. One is that we forgot to set the "secondary" bit in the hash PTEs when hashing a huge page in the secondary bucket (fortunately very rare). The other one is on non-LPAR machines (like Apple G5s), flush_hash_range() which is used to flush a batch of PTEs simply did not work for huge pages. Historically, our huge page code didn't batch, but this was changed without fixing this routine. This patch fixes both. Signed-off-by: Benjamin Herrenschmidt <benh@kernel.crashing.org> Signed-off-by: Andrew Morton <akpm@osdl.org> Signed-off-by: Linus Torvalds <torvalds@osdl.org>
This commit is contained in:
parent
2601c2e278
commit
67b108131d
@ -343,9 +343,7 @@ static void native_flush_hash_range(unsigned long context,
|
||||
hpte_t *hptep;
|
||||
unsigned long hpte_v;
|
||||
struct ppc64_tlb_batch *batch = &__get_cpu_var(ppc64_tlb_batch);
|
||||
|
||||
/* XXX fix for large ptes */
|
||||
unsigned long large = 0;
|
||||
unsigned long large;
|
||||
|
||||
local_irq_save(flags);
|
||||
|
||||
@ -358,6 +356,7 @@ static void native_flush_hash_range(unsigned long context,
|
||||
|
||||
va = (vsid << 28) | (batch->addr[i] & 0x0fffffff);
|
||||
batch->vaddr[j] = va;
|
||||
large = pte_huge(batch->pte[i]);
|
||||
if (large)
|
||||
vpn = va >> HPAGE_SHIFT;
|
||||
else
|
||||
|
@ -710,10 +710,13 @@ int hash_huge_page(struct mm_struct *mm, unsigned long access,
|
||||
hpte_group = ((~hash & htab_hash_mask) *
|
||||
HPTES_PER_GROUP) & ~0x7UL;
|
||||
slot = ppc_md.hpte_insert(hpte_group, va, prpn,
|
||||
HPTE_V_LARGE, rflags);
|
||||
HPTE_V_LARGE |
|
||||
HPTE_V_SECONDARY,
|
||||
rflags);
|
||||
if (slot == -1) {
|
||||
if (mftb() & 0x1)
|
||||
hpte_group = ((hash & htab_hash_mask) * HPTES_PER_GROUP) & ~0x7UL;
|
||||
hpte_group = ((hash & htab_hash_mask) *
|
||||
HPTES_PER_GROUP)&~0x7UL;
|
||||
|
||||
ppc_md.hpte_remove(hpte_group);
|
||||
goto repeat;
|
||||
|
Loading…
Reference in New Issue
Block a user