On 14/07/2026 16:04, Kevin Brodsky wrote:
> Commit 8b1cb4a2e819 ("mm/pagewalk: fix EFI_PGT_DUMP of
> espfix area") made no-VMA page table walks use
> pte_offset_kernel() for any address above TASK_SIZE. This avoided
> pte_offset_map() validation on EFI page table dumps, where efi_mm
> could walk x86 espfix PMDs that intentionally look bad to pmd_bad().

Sashiko rightly doesn't like this patch. Turns out 8b1cb4a2e819's commit
message and the comment it added are narrower than what the problem
really is: on x86, due to things like
/sys/kernel/debug/page_tables/current_kernel, we may be walking kernel
page tables even when walk->mm is a regular user mm. Just checking the
mm is therefore not sufficient.

Will replace this patch with a rewording of the comment to avoid
suggesting the issue is specific to efi_mm.

- Kevin


> efi_mm is now marked with MMF_KERNEL, and no-VMA walks use
> mm_is_kernel() to select pte_offset_kernel() for kernel mm's. As a
> result we no longer need to handle the EFI_PGT_DUMP case explicitly.The
> address check is therefore redundant for EFI_PGT_DUMP and makes the
> condition harder to reason about.
>
> Remove the address check and associated comment; mm_is_kernel()
> should be sufficient on its own.
>
> Tested by booting x86 QEMU with CONFIG_EFI_PGT_DUMP=y and reading
> /sys/kernel/debug/page_tables/efi.
>
> Assisted-by: Codex:GPT-5.5
> Signed-off-by: Kevin Brodsky <[email protected]>
> ---
>  mm/pagewalk.c | 7 ++-----
>  1 file changed, 2 insertions(+), 5 deletions(-)
>
> diff --git a/mm/pagewalk.c b/mm/pagewalk.c
> index a3f47d1de3c5..0dd9d4ad9b68 100644
> --- a/mm/pagewalk.c
> +++ b/mm/pagewalk.c
> @@ -68,17 +68,14 @@ static int walk_pte_range(pmd_t *pmd, unsigned long addr, 
> unsigned long end,
>       if (walk->no_vma) {
>               /*
>                * pte_offset_map() might apply user-specific validation.
> -              * Indeed, on x86_64 the pmd entries set up by init_espfix_ap()
> -              * fit its pmd_bad() check (_PAGE_NX set and _PAGE_RW clear),
> -              * and CONFIG_EFI_PGT_DUMP efi_mm goes so far as to walk them.
>                */
> -             if (mm_is_kernel(walk->mm) || addr >= TASK_SIZE)
> +             if (mm_is_kernel(walk->mm))
>                       pte = pte_offset_kernel(pmd, addr);
>               else
>                       pte = pte_offset_map(pmd, addr);
>               if (pte) {
>                       err = walk_pte_range_inner(pte, addr, end, walk);
> -                     if (!mm_is_kernel(walk->mm) && addr < TASK_SIZE)
> +                     if (!mm_is_kernel(walk->mm))
>                               pte_unmap(pte);
>               }
>       } else {
>

Reply via email to