Re: [PATCH v6] mm: retry page faults once under the per-VMA lock

From: Lorenzo Stoakes (ARM)

Date: Tue Oct 27 2026 - 12:46:40 EST


On Tue, Oct 27, 2026 at 04:26:39PM +0000, Lorenzo Stoakes (ARM) wrote:
>
> Thread A (Parent) | Thread B (Parent) | Thread C (Parent)
> ---------------------------|-------------------------|----------------------
> < Fork > | | < has TLB entry >
> copy_present_ptes() | < no TLB entry > |
> wrprotect parent page X | |
> -> 2 mappings, refs | *ptr = x |
> | < Page fault > |
> | do_wp_page() |
> | < shared, so CoW > |
> | wp_page_copy() |
> | copy X -> new pg N |
> | | *ptr = x;
> | | [ OOPS! stale TLB,
> | | lands in X not N ]
> | ptep_clear_flush() |
> | < TLB flush > |
> | parent PTE -> N |
> | [ X now child-only ]|
> | | ASSERT(*ptr == x);
> flush_tlb_mm(oldmm) | | // fails! N lacks x
> < far too late > | |
>

Sigh, I drew this entirely manually, then had the LLM overlords 'correct' it,
but it also made it less clear :).

Thread C ends up writing to what-becomes-the-child-page X, whereas the parent
ends up with page N after CoW.

So a thread in the parent writes to a page of ordinary memory and then it
disappears under them, and the child ends up with corruption in their page.

--
Cheers, Lorenzo