x86: check PMD in spurious_fault handler
Impact: fix to prevent hard lockup on bad PMD permissions If the PMD does not have the correct permissions for a page access, but the PTE does, the spurious fault handler will mistake the fault as a lazy TLB transaction. This will result in an infinite loop of: fault -> spurious_fault check (pass) -> return to code -> fault This patch adds a check and a warn on if the PTE passes the permissions but the PMD does not. [ Updated: Ingo Molnar suggested using WARN_ONCE with some text ] Signed-off-by: Steven Rostedt <srostedt@redhat.com>
This commit is contained in:
parent
07a66d7c53
commit
3c3e5694ad
|
@ -455,6 +455,7 @@ static int spurious_fault(unsigned long address,
|
||||||
pud_t *pud;
|
pud_t *pud;
|
||||||
pmd_t *pmd;
|
pmd_t *pmd;
|
||||||
pte_t *pte;
|
pte_t *pte;
|
||||||
|
int ret;
|
||||||
|
|
||||||
/* Reserved-bit violation or user access to kernel space? */
|
/* Reserved-bit violation or user access to kernel space? */
|
||||||
if (error_code & (PF_USER | PF_RSVD))
|
if (error_code & (PF_USER | PF_RSVD))
|
||||||
|
@ -482,7 +483,17 @@ static int spurious_fault(unsigned long address,
|
||||||
if (!pte_present(*pte))
|
if (!pte_present(*pte))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
return spurious_fault_check(error_code, pte);
|
ret = spurious_fault_check(error_code, pte);
|
||||||
|
if (!ret)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Make sure we have permissions in PMD
|
||||||
|
* If not, then there's a bug in the page tables.
|
||||||
|
*/
|
||||||
|
ret = spurious_fault_check(error_code, (pte_t *) pmd);
|
||||||
|
WARN_ONCE(!ret, "PMD has incorrect permission bits\n");
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
Loading…
Reference in New Issue