From nobody Sat Jul 25 23:05:42 2026 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-alma10-1.taild15c8.ts.net [100.103.45.18]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 1330930568B; Sun, 12 Jul 2026 10:44:22 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=100.103.45.18 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783853065; cv=none; b=k7VXojkon6VbCW/B5OSv7gU4zf8rybbdCSz1HJdwDb14CRf1nE+IWC8r/VSOnPc4H8x6OHkvrYrW3KTWL7ep+fMx4q7eZyOWE5ms+reFTpeaXOuT/9AjcOtmZ55uWrfBGQYxKpVBki3NRQwAm5HIbAEDvLN380QMy7wX5LIQoDA= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783853065; c=relaxed/simple; bh=xQodVoiXdDrJKxRsliP+fCQ/22OZXiwGI+7CmkHVdwg=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=mISkXPMPEkS8I/Rb5BSag8E01z8HK3ANkH5YJkJOAUdSwXwW62k6BoxSbhWbuT17NhZnx6QbFyzw1RBniIIDBlI7XjLU5jDaZNXai5VOgoq9cTFjOi3wrebejs4UytkvOwg6sYkuJlJnzxhtlIw2E+Hkk9lLlOmplx/dwJJYsno= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b=kNSp2fhA; arc=none smtp.client-ip=100.103.45.18 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b="kNSp2fhA" Received: by smtp.kernel.org (Postfix) with ESMTPSA id 026F51F00A3A; Sun, 12 Jul 2026 10:44:15 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=kernel.org; s=k20260515; t=1783853062; bh=zpPQrWrhaa9UNndbmcx8A6wGwMbr3pW1qCJ/JB1tuhc=; h=From:Date:Subject:References:In-Reply-To:To:Cc; b=kNSp2fhA4GIlbE62mL2Z8FrYKasEjgKZsF3b0rA+28FKqQZrTdfSftLk9RuV+5XrT MunEzauTlLTS+W4xYOlz/qVyH893DoSKzVQb9EuFKWLMtMm3KASZE452GOzwQMeM8o g90c6npA6AIsJG0iErJZgrDBcc6sA92xyw2KrTo5140Ag9MYNfGansJWdTi9UrBDer 058eIKu71qMblp/6gcmQXbRLNcI1ouLLReKusTGAY2McMW94EALI4yFtQxj9bAWHkW +BIaHyzuOBeGRDOK7OwfLRmjlnUNtO0baD8QdrGREqBPBk97zlYt6Ya8od9NcmnMjF HTIzsWRwP8fUw== From: Lorenzo Stoakes Date: Sun, 12 Jul 2026 11:42:24 +0100 Subject: [PATCH mm-hotfixes v2 1/4] mm/vmalloc: acquire init_mm lock on huge vmap to avoid ptdump UAF Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Message-Id: <20260712-series-vmap-race-fix-v2-1-ad134cc3a12a@kernel.org> References: <20260712-series-vmap-race-fix-v2-0-ad134cc3a12a@kernel.org> In-Reply-To: <20260712-series-vmap-race-fix-v2-0-ad134cc3a12a@kernel.org> To: Andrew Morton , Suren Baghdasaryan , "Liam R. Howlett" , Vlastimil Babka , Shakeel Butt , David Hildenbrand , Mike Rapoport , Michal Hocko , Uladzislau Rezki , Toshi Kani , Dave Hansen , Andy Lutomirski , Peter Zijlstra , Thomas Gleixner , Ingo Molnar , Borislav Petkov , x86@kernel.org, "H. Peter Anvin" , Kiryl Shutsemau , Catalin Marinas , Will Deacon , Dev Jain , Ryan Roberts Cc: David Carlier , ljs@kernel.org, linux-mm@kvack.org, linux-kernel@vger.kernel.org, bpf@vger.kernel.org, linux-arm-kernel@lists.infradead.org, stable@vger.kernel.org, syzbot+fd95a72470f5a44e464c@syzkaller.appspotmail.com X-Mailer: b4 0.15.2 X-Developer-Signature: v=1; a=openpgp-sha256; l=10169; i=ljs@kernel.org; h=from:subject:message-id; bh=xQodVoiXdDrJKxRsliP+fCQ/22OZXiwGI+7CmkHVdwg=; b=owGbwMvMwCV2fu7ZrsZH9SKMp9WSGLKC8z9IdUf8z3HhZwvamlaVZzaFs66mrXCKzT3Vo62/z /vLcBV3lLIwiHExyIopsjz/Ir4/SCRsXucFfzeYOaxMIEMYuDgFYCIFFxgZrhoueHDxzxvO8u1B T20YZ3YV6Zv8ttu360Pdm+qbXowbRBj+mRvPe/lkrbD48je5pwUSmf9/u/fPX9bXdoqkDAvnerY YBgA= X-Developer-Key: i=ljs@kernel.org; a=openpgp; fpr=E7F417BF5214569E89D04F46CF9DCD8A81E27F14 Currently there is a nasty race between ptdump and vmap when attempting to map a huge P4D, PMD or PUD entry. ptdump is invoked by arch code to walk kernel or EFI page tables, either to output it for debugging purposes, or to assert that there are no W+X (i.e. executable writable pages) exposed in these ranges. The feature is enabled generally via CONFIG_PTDUMP (whose implementation is in mm/ptdump.c), and expose a debugfs interface for it if CONFIG_PTDUMP_DEBUGFS is defined. If CONFIG_PTDUMP is enabled, then /sys/kernel/debug/check_wx_pages is enabled which checks kernel ranges to perform the W+X check. If CONFIG_DEBUG_WX is enabled, this is done on boot. (Note that arm32 implements its own page table walker and uses CONFIG_ARM_DEBUG_WX and CONFIG_ARM_PTDUMP_DEBUGFS for this.) The EFI implementations vary by architecture, but are not relevant to the bug, as the issue is when kernel page ranges are walked. ptdump_walk_pgd() holds both the mem hotplug lock and the mmap write lock before invoking walk_page_range_debug(), however this runs into an issue with vmalloc ranges. When vmap maps a P4D, PUD or a PMD sized range and encounters an existing P4d/PUD/PMD entry pointing to a PUD/PMD/PTE page table, it invokes vmap_try_huge_[p4d,pud,pmd]() to try to convert it to a huge page table mapping if possible. However, when it does this, it holds no meaningful locks against other kernel page table walkers, invoking [p4d,pud,pmd]_free_[pud,pmd,pte]_page() which calls pagetable_free() and pagetable_free_kernel() in turn (pte_fragment_free() for powerpc). This means that a use-after-free becomes possible if the ptdump page table walker happens to be walking a PUD, PMD or PTE page table after it has been freed. Since commit 5ba2f0a15564 ("mm: introduce deferred freeing for kernel page tables"), if CONFIG_ASYNC_KERNEL_PGTABLE_FREE is set, pagetable_free_kernel() will batch the page table freeing operation, otherwise it frees the page table directly. While the KASAN report that syzbot highlighted indicated that the issue arose in a workqueue introduced by this change, this is coincidental and the commit did not alter the race which has existed for quite some time. This patch resolves the issue by simply having vmap_try_huge_[p4d,pud,pmd]() hold the mmap read lock on init_mm while invoking [p4d,pud,pmd]_free_[pud,pmd,pte]_page() and [p4d,pud,pmd]_set_huge(). This way, page table walkers either observe a newly promoted huge P4D/PUD/PMD leaf entry or the prior PUD/PMD/PTE entry and never get passed a dangling pointer, whether the page is freed asynchronously or not. All other kernel page table walkers that touch vmalloc ranges either exclusively own the memory walked or acquire the mmap lock, so this correctly excludes those walkers. We acquire the mmap read lock as a trylock, as this is an optimisation that is permitted not to succeed, a race is very unlikely, and doing so eliminates latency sleeping on the lock would have otherwise caused. We also define a guard class for mmap_read_trylock() so we can use cleanup.h to make the scope handling cleaner in the implementation. One wrinkle here is commit fa93b45fd397 ("arm64: Enable vmalloc-huge with ptdump"), which addresses the issue for arm64 only by explicitly acquiring the mmap read lock on kernel page table freeing should a concurrent ptdump be in progress. This is problematic as vmap may acquire the mmap read lock prior to ptdump attempting to acquire an mmap write lock, leading to a deadlock when the mmap read lock is slept upon on page table freeing due to rwsem anti-starvation. We work around this by predicating the mmap lock being taken on !CONFIG_ARM64 for the time being. With this patch applied, a follow up will partially revert commit fa93b45fd397 ("arm64: Enable vmalloc-huge with ptdump") and at that stage remove the arm64 ifdeffery. We also update walk_page_range_debug() to assert the mmap write lock unconditionally and update the comment here to reflect this change. The issue has existed as long as ptdump was available and vmap freed page tables when promoting to a huge leaf entry, that is, since commit b6bdb7517c3d ("mm/vmalloc: add interfaces to free unmapped page table") for huge ioremap, and commit 121e6f3258fe ("mm/vmalloc: hugepage vmalloc mappings") for huge vmalloc. Since the former is the earlier of the two we choose that for our Fixes tag. This patch is based on work by David Carlier (linked), with gratitude! Fixes: b6bdb7517c3d ("mm/vmalloc: add interfaces to free unmapped page tabl= e") Cc: stable@vger.kernel.org Reported-by: syzbot+fd95a72470f5a44e464c@syzkaller.appspotmail.com Closes: https://lore.kernel.org/all/6a287988.39669fcc.33b062.00a0.GAE@googl= e.com/T/ Link: https://lore.kernel.org/linux-mm/20260706203128.162335-1-devnexen@gma= il.com/ Reviewed-by: Mike Rapoport (Microsoft) Signed-off-by: Lorenzo Stoakes Reviewed-by: Dev Jain --- include/linux/mmap_lock.h | 1 + mm/pagewalk.c | 22 +++++++++++---------- mm/vmalloc.c | 50 ++++++++++++++++++++++++++++++++++++++-----= ---- 3 files changed, 54 insertions(+), 19 deletions(-) diff --git a/include/linux/mmap_lock.h b/include/linux/mmap_lock.h index 04b8f61ece5d..6b5c2390cc30 100644 --- a/include/linux/mmap_lock.h +++ b/include/linux/mmap_lock.h @@ -621,6 +621,7 @@ static inline void mmap_read_unlock(struct mm_struct *m= m) =20 DEFINE_GUARD(mmap_read_lock, struct mm_struct *, mmap_read_lock(_T), mmap_read_unlock(_T)) +DEFINE_GUARD_COND(mmap_read_lock, _try, mmap_read_trylock(_T)) =20 static inline void mmap_read_unlock_non_owner(struct mm_struct *mm) { diff --git a/mm/pagewalk.c b/mm/pagewalk.c index 3ae2586ff45b..bbcfd68d0907 100644 --- a/mm/pagewalk.c +++ b/mm/pagewalk.c @@ -678,6 +678,8 @@ int walk_kernel_page_table_range_lockless(unsigned long= start, unsigned long end * will also not lock the PTEs for the pte_entry() callback. * * This is for debugging purposes ONLY. + * + * The mmap write lock must be held. */ int walk_page_range_debug(struct mm_struct *mm, unsigned long start, unsigned long end, const struct mm_walk_ops *ops, @@ -691,6 +693,16 @@ int walk_page_range_debug(struct mm_struct *mm, unsign= ed long start, .no_vma =3D true }; =20 + /* + * When walking userland page tables, an mmap write lock must be held to + * account for munmap() downgrading to an mmap read lock when tearing + * down page tables. + * + * When walking kernel page tables, an mmap write lock must also be held + * to account for page table freeing on vmap huge page mapping. + */ + mmap_assert_write_locked(mm); + /* For convenience, we allow traversal of kernel mappings. */ if (mm =3D=3D &init_mm) return walk_kernel_page_table_range(start, end, ops, @@ -700,16 +712,6 @@ int walk_page_range_debug(struct mm_struct *mm, unsign= ed long start, if (!check_ops_safe(ops)) return -EINVAL; =20 - /* - * The mmap lock protects the page walker from changes to the page - * tables during the walk. However a read lock is insufficient to - * protect those areas which don't have a VMA as munmap() detaches - * the VMAs before downgrading to a read lock and actually tearing - * down PTEs/page tables. In which case, the mmap write lock should - * be held. - */ - mmap_assert_write_locked(mm); - return walk_pgd_range(start, end, &walk); } =20 diff --git a/mm/vmalloc.c b/mm/vmalloc.c index 1afca3568b9b..1fa9ac6e43d4 100644 --- a/mm/vmalloc.c +++ b/mm/vmalloc.c @@ -43,6 +43,7 @@ #include #include #include +#include =20 #define CREATE_TRACE_POINTS #include @@ -158,10 +159,25 @@ static int vmap_try_huge_pmd(pmd_t *pmd, unsigned lon= g addr, unsigned long end, if (!IS_ALIGNED(phys_addr, PMD_SIZE)) return 0; =20 - if (pmd_present(*pmd) && !pmd_free_pte_page(pmd, addr)) - return 0; + if (!pmd_present(*pmd)) + return pmd_set_huge(pmd, phys_addr, prot); =20 - return pmd_set_huge(pmd, phys_addr, prot); + /* + * Kernel page table walkers either walk ranges they own exclusively or + * hold the mmap write lock on init_mm (ptdump being the motivating + * case). + * + * Therefore, acquire the mmap read lock to prevent use-after-free when + * freeing page tables. + */ +#ifndef CONFIG_ARM64 + scoped_cond_guard(mmap_read_lock_try, return 0, &init_mm) +#endif + { + if (!pmd_free_pte_page(pmd, addr)) + return 0; + return pmd_set_huge(pmd, phys_addr, prot); + } } =20 static int vmap_pmd_range(pud_t *pud, unsigned long addr, unsigned long en= d, @@ -210,10 +226,18 @@ static int vmap_try_huge_pud(pud_t *pud, unsigned lon= g addr, unsigned long end, if (!IS_ALIGNED(phys_addr, PUD_SIZE)) return 0; =20 - if (pud_present(*pud) && !pud_free_pmd_page(pud, addr)) - return 0; + if (!pud_present(*pud)) + return pud_set_huge(pud, phys_addr, prot); =20 - return pud_set_huge(pud, phys_addr, prot); + /* See comment in vmap_try_huge_pmd(). */ +#ifndef CONFIG_ARM64 + scoped_cond_guard(mmap_read_lock_try, return 0, &init_mm) +#endif + { + if (!pud_free_pmd_page(pud, addr)) + return 0; + return pud_set_huge(pud, phys_addr, prot); + } } =20 static int vmap_pud_range(p4d_t *p4d, unsigned long addr, unsigned long en= d, @@ -262,10 +286,18 @@ static int vmap_try_huge_p4d(p4d_t *p4d, unsigned lon= g addr, unsigned long end, if (!IS_ALIGNED(phys_addr, P4D_SIZE)) return 0; =20 - if (p4d_present(*p4d) && !p4d_free_pud_page(p4d, addr)) - return 0; + if (!p4d_present(*p4d)) + return p4d_set_huge(p4d, phys_addr, prot); =20 - return p4d_set_huge(p4d, phys_addr, prot); + /* See comment in vmap_try_huge_pmd(). */ +#ifndef CONFIG_ARM64 + scoped_cond_guard(mmap_read_lock_try, return 0, &init_mm) +#endif + { + if (!p4d_free_pud_page(p4d, addr)) + return 0; + return p4d_set_huge(p4d, phys_addr, prot); + } } =20 static int vmap_p4d_range(pgd_t *pgd, unsigned long addr, unsigned long en= d, --=20 2.55.0 From nobody Sat Jul 25 23:05:42 2026 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-alma10-1.taild15c8.ts.net [100.103.45.18]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 2ECEB3749ED; Sun, 12 Jul 2026 10:44:30 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=100.103.45.18 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783853071; cv=none; b=jQqMdwh1ESUVIK2FAXRpJtwaJ7L0ZaQwmHUFDIJ7jzPCskGNUd8fd4ZmAg/o23BQVHgebJYrozeRl4L3n7JSMVdMHacvCVEDKTcCtyJ8tNpr/ACwEWSTcpBory05zb6YeBh6zrwoJqApGLTNePleW9j626bcjUV+s3tyQlgo6DY= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783853071; c=relaxed/simple; bh=sQJwBcRAluqgPNbXUgxA0+sFptVnbX0UWpL7em1s+OU=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=uM/7C1x3sjWzRx+7BtEVapDVa/9/DEVEDTWEmHKBqOxlGl79snIXHWntKz67Aj7eqwH8WGxPTfRhDRZoVgxJ4QMI+Wz7TBO7AzT2iNvBw7Ex5chQ27Hrrf1R51BsgUdRJpewZe56uGXloIrEgphHJ2exDLymyXA45A1olZrSuPQ= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b=OG39gJMG; arc=none smtp.client-ip=100.103.45.18 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b="OG39gJMG" Received: by smtp.kernel.org (Postfix) with ESMTPSA id 4D7AF1F000E9; Sun, 12 Jul 2026 10:44:23 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=kernel.org; s=k20260515; t=1783853069; bh=vGAlEpRQYRhrbsbyFqevUzGTrHwI86sKZ3VuDai3N60=; h=From:Date:Subject:References:In-Reply-To:To:Cc; b=OG39gJMG3+GR+z2BP91RhW1g0+wE49EpUq3bCYDPV/qd1d16HjQxfaa5OvRrLt4t1 ScfsqVHBbYXGzWg1Ng0Uj61vjOdBG8skAeWgfl7mfu6l7WzjPmPBw5s3GsYjHbHBlI P/6KwDeXesk2Y9ik3ih48WxLLm6+kKD93yq/NveeZMCdB6kOcqbl2f9rI+pyDoYAwd CRwwmI70HYUvVJv4l3pVq9XKKrd27HOgHknKzrBrcIU2KRSA+jkHv+eoW++NJrOfuW 3YfKKI6vu+vOm3Kuy+pv3wszW47DA7g5awhjYFtsysatnbJHTTMialqgKQOD3Jfw5R 1t1JytAS9BmOg== From: Lorenzo Stoakes Date: Sun, 12 Jul 2026 11:42:25 +0100 Subject: [PATCH mm-hotfixes v2 2/4] x86/mm/pat: acquire mmap lock on page table free to avoid ptdump UAF Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Message-Id: <20260712-series-vmap-race-fix-v2-2-ad134cc3a12a@kernel.org> References: <20260712-series-vmap-race-fix-v2-0-ad134cc3a12a@kernel.org> In-Reply-To: <20260712-series-vmap-race-fix-v2-0-ad134cc3a12a@kernel.org> To: Andrew Morton , Suren Baghdasaryan , "Liam R. Howlett" , Vlastimil Babka , Shakeel Butt , David Hildenbrand , Mike Rapoport , Michal Hocko , Uladzislau Rezki , Toshi Kani , Dave Hansen , Andy Lutomirski , Peter Zijlstra , Thomas Gleixner , Ingo Molnar , Borislav Petkov , x86@kernel.org, "H. Peter Anvin" , Kiryl Shutsemau , Catalin Marinas , Will Deacon , Dev Jain , Ryan Roberts Cc: David Carlier , ljs@kernel.org, linux-mm@kvack.org, linux-kernel@vger.kernel.org, bpf@vger.kernel.org, linux-arm-kernel@lists.infradead.org, stable@vger.kernel.org X-Mailer: b4 0.15.2 X-Developer-Signature: v=1; a=openpgp-sha256; l=2980; i=ljs@kernel.org; h=from:subject:message-id; bh=sQJwBcRAluqgPNbXUgxA0+sFptVnbX0UWpL7em1s+OU=; b=owGbwMvMwCV2fu7ZrsZH9SKMp9WSGLKC8z/859bu7Nn3SrLd4LHMIr6D0jnXY99ZKqtbpX9kV OT/stito5SFQYyLQVZMkeX5F/H9QSJh8zov+LvBzGFlAhnCwMUpABM5/Ijhr6Dyad2m2Y0q1/o6 318LY3hTsNKyT3Nhxsk5k77/Ot/rfZnhv9vCUB9Bu4mFD7RKpLdoGlw2+/rkXRibwL4ZEbMTvv2 yYAMA X-Developer-Key: i=ljs@kernel.org; a=openpgp; fpr=E7F417BF5214569E89D04F46CF9DCD8A81E27F14 x86 implements page attribute modification using its Change Page Attributes (CPA) mechanism. This tracks properties of ranges such as cache mode through x86 page attributes, and as part of that logic manipulates kernel page tables. Since commit 41d88484c71c ("x86/mm/pat: restore large ROX pages after fragmentation") ranges of kernel page table entries can be collapsed into huge page table entries as part of this logic. As part of this collapse, it frees the page tables which the collapsed entries previously pointed to, and it does so without any relevant locks being held to preclude concurrent kernel page table walkers. The only way this code can be reached is if CPA_COLLAPSE is specified, and this is only set in set_memory_rox() via: set_memory_rox() -> change_page_attr_set_clr() -> cpa_flush() -> cpa_collapse_large_pages() Notable users of this are execmem and bpf when manipulating executable mappings. However, this is problematic for ptdump, as it walks ranges it does not own and thus runs the risk of a use-after-free on page tables freed underneath it. This patch resolves the issue by acquiring the mmap read lock on init_mm to provide mutual exclusion against ptdump, which acquires the init_mm write lock. It is safe to acquire a sleeping lock as all the callers invoke set_memory_rox() from process context and in any case, change_page_attr_set_clr() calls vm_unmap_alias() which ultimately takes a mutex, disallowing atomic context here. We also include cleanup.h in order to use a scoped_guard() to implement this cleanly. Fixes: 41d88484c71c ("x86/mm/pat: restore large ROX pages after fragmentati= on") Cc: stable@vger.kernel.org Reviewed-by: Mike Rapoport (Microsoft) Reviewed-by: Kiryl Shutsemau (Meta) Signed-off-by: Lorenzo Stoakes --- arch/x86/mm/pat/set_memory.c | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-) diff --git a/arch/x86/mm/pat/set_memory.c b/arch/x86/mm/pat/set_memory.c index d023a40a1e03..4c4b8244502f 100644 --- a/arch/x86/mm/pat/set_memory.c +++ b/arch/x86/mm/pat/set_memory.c @@ -22,6 +22,7 @@ #include #include #include +#include =20 #include #include @@ -436,9 +437,16 @@ static void cpa_collapse_large_pages(struct cpa_data *= cpa) =20 flush_tlb_all(); =20 - list_for_each_entry_safe(ptdesc, tmp, &pgtables, pt_list) { - list_del(&ptdesc->pt_list); - pagetable_free(ptdesc); + /* + * ptdump might read these page tables, so avoid a use-after-free by + * acquiring the mmap read lock on init_mm (ptdump acquires the mmap + * write lock). + */ + scoped_guard(mmap_read_lock, &init_mm) { + list_for_each_entry_safe(ptdesc, tmp, &pgtables, pt_list) { + list_del(&ptdesc->pt_list); + pagetable_free(ptdesc); + } } } =20 --=20 2.55.0 From nobody Sat Jul 25 23:05:42 2026 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-alma10-1.taild15c8.ts.net [100.103.45.18]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 636FD3749ED; Sun, 12 Jul 2026 10:44:37 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=100.103.45.18 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783853078; cv=none; b=gdc9wRn3KNJbhthDBWnOOTS9hXLa67UKp15KDLDZznwrKZlp+5UwLPG9O/Z6FWyeYgfo7K+i3Ot6yhcuPbclj6KogJ4t+DLlu0G5atTlAJ6BNAjKQJYQVdL0R4FSDAqlyhCsJz/dBJOLyHv7uLeEbjl35ZETf6RdfOn/+3KqO/0= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783853078; c=relaxed/simple; bh=wPiaIn6Wg5e3GQRwvp54WRABlKxC65yqG85hBilGX1E=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=ktHwW8rD9T9BO/hEzDdN7rK3mnWwLLY7pfhJCXHrQezkqo2GUIHErfbWQBVVxsCPa2qBf23SqUGGYJ5gmaR8AZQhzbHlU/zOhAMEljuLwwv7l4luny9pZ3e0WShKtlWDmu6cOUM4c2kOYsos70UncHZaGNT6iUfwZmtN+kOsX3U= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b=Omw7G4Fg; arc=none smtp.client-ip=100.103.45.18 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b="Omw7G4Fg" Received: by smtp.kernel.org (Postfix) with ESMTPSA id 64F781F00A3A; Sun, 12 Jul 2026 10:44:30 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=kernel.org; s=k20260515; t=1783853077; bh=nrk8vC+Ve+FQgyHSJEFAxaMx0g8ZadKX9MusPiIExkE=; h=From:Date:Subject:References:In-Reply-To:To:Cc; b=Omw7G4FgNZYcZEmrx511ChY6T9zMUkEWv+kAbym3JjUrya1Ou8V/rBt5Kef5Y7zYC 53+LYE4FKKsaE+qXpZWHu9nunSk9FGUVcxUDkahaqAQEXZSPDVd98i7drMhzaHWP2a RPkASOS+rmfEXYteYtuCZMoA83Jqwo2NEGTNo2xnKmIALLwHG+Jbrg1e/MHlOnR/JC meTFrDK0xcA+0UC47jl+ixZ4bNZ3Uer2PUPO8gfA1enw0fTLJBnVbL+9aUNBKGqNei ZLlkOFBJs7UCBRnreuH5WVcET8q4FiCYohUpl9FUxY6V6Ejbfr+rQqt6KgIcjYj1fH rACwlkoNj+0Ig== From: Lorenzo Stoakes Date: Sun, 12 Jul 2026 11:42:26 +0100 Subject: [PATCH mm-hotfixes v2 3/4] mm/ptdump: always stabilise against page table freeing using init_mm Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Message-Id: <20260712-series-vmap-race-fix-v2-3-ad134cc3a12a@kernel.org> References: <20260712-series-vmap-race-fix-v2-0-ad134cc3a12a@kernel.org> In-Reply-To: <20260712-series-vmap-race-fix-v2-0-ad134cc3a12a@kernel.org> To: Andrew Morton , Suren Baghdasaryan , "Liam R. Howlett" , Vlastimil Babka , Shakeel Butt , David Hildenbrand , Mike Rapoport , Michal Hocko , Uladzislau Rezki , Toshi Kani , Dave Hansen , Andy Lutomirski , Peter Zijlstra , Thomas Gleixner , Ingo Molnar , Borislav Petkov , x86@kernel.org, "H. Peter Anvin" , Kiryl Shutsemau , Catalin Marinas , Will Deacon , Dev Jain , Ryan Roberts Cc: David Carlier , ljs@kernel.org, linux-mm@kvack.org, linux-kernel@vger.kernel.org, bpf@vger.kernel.org, linux-arm-kernel@lists.infradead.org, stable@vger.kernel.org X-Mailer: b4 0.15.2 X-Developer-Signature: v=1; a=openpgp-sha256; l=3713; i=ljs@kernel.org; h=from:subject:message-id; bh=wPiaIn6Wg5e3GQRwvp54WRABlKxC65yqG85hBilGX1E=; b=owGbwMvMwCV2fu7ZrsZH9SKMp9WSGLKC8z9MUr22dUnwgTM3Wrcan9b9lrw17t3yC79mtJow6 feuMeBU7ChlYRDjYpAVU2R5/kV8f5BI2LzOC/5uMHNYmUCGMHBxCsBE+LgYGfpan6zcqfjrdp5G fef1L7Mjl5o0GN48fZebk+PG7VNz9EUZGXayf+xZ9H+hSuQB0ZL2MPnuKyz3DYyPTH3w3i3KS++ iPQsA X-Developer-Key: i=ljs@kernel.org; a=openpgp; fpr=E7F417BF5214569E89D04F46CF9DCD8A81E27F14 x86 and arm64 invoke ptdump_walk_pgd() with non-init_mm mm whilst still walking kernel page table ranges. For x86 this is done in ptdump_curknl_show() and ptdump_efi_show(), the first passing current->mm, and the second passing efi_mm (we reach kernel mappings that init_mm protects for current->mm due to x86 cloning shared kernel page tables for arbitrary mm's). arm64 does so via ptdump_debugfs_register(), configured by efi_ptdump_info for efi ranges against efi_mm. The init_mm mmap lock is used to stabilise page table freeing against ptdump, so take a nested lock on init_mm to ensure that we are correctly stabilised. We take this after mmap write locking the non-init_mm mm. Nothing acquires the init_mm lock first before locking an arbitrary mm, so no deadlock is possible. The preceding patches in this series updated the two cases which can cause races with ptdump in init_mm ranges - vmap and x86 CPA huge page promotion. For arm64, commit fa93b45fd397 ("arm64: Enable vmalloc-huge with ptdump") already provides exclusion against init_mm for the vmap case, which this patch also pairs with. The first point at which ptdump can race kernel page table freeing is commit b6bdb7517c3d ("mm/vmalloc: add interfaces to free unmapped page table"), so we target this in the Fixes tag. Also update walk_page_range_debug() to assert that init_mm is write locked, add a comment explaining why and remove some redundant code. We do not need to check for walk.mm being non-NULL, as the mmap lock asserts would NULL pointer deref if it was (and of course no callers do this). The rest of this code is exactly as it would be if invoking walk_kernel_page_table_range(), only now it's far clearer that that's the case. Fixes: b6bdb7517c3d ("mm/vmalloc: add interfaces to free unmapped page tabl= e") Cc: stable@vger.kernel.org Reviewed-by: Mike Rapoport (Microsoft) Signed-off-by: Lorenzo Stoakes --- mm/pagewalk.c | 14 +++++++++----- mm/ptdump.c | 7 +++++++ 2 files changed, 16 insertions(+), 5 deletions(-) diff --git a/mm/pagewalk.c b/mm/pagewalk.c index bbcfd68d0907..5d87c632a255 100644 --- a/mm/pagewalk.c +++ b/mm/pagewalk.c @@ -702,12 +702,16 @@ int walk_page_range_debug(struct mm_struct *mm, unsig= ned long start, * to account for page table freeing on vmap huge page mapping. */ mmap_assert_write_locked(mm); + /* + * x86, arm64 ptdump allow walks of efi mm's and x86 ptdump allows walks + * of arbitrary mm's. + * + * However, they both must also hold the init_mm lock to account for + * concurrent kernel page table freeing. + */ + mmap_assert_write_locked(&init_mm); =20 - /* For convenience, we allow traversal of kernel mappings. */ - if (mm =3D=3D &init_mm) - return walk_kernel_page_table_range(start, end, ops, - pgd, private); - if (start >=3D end || !walk.mm) + if (start >=3D end) return -EINVAL; if (!check_ops_safe(ops)) return -EINVAL; diff --git a/mm/ptdump.c b/mm/ptdump.c index 973020000096..5851096e6f65 100644 --- a/mm/ptdump.c +++ b/mm/ptdump.c @@ -178,11 +178,18 @@ void ptdump_walk_pgd(struct ptdump_state *st, struct = mm_struct *mm, pgd_t *pgd) =20 get_online_mems(); mmap_write_lock(mm); + /* To stabilise kernel page tables we must hold the init_mm lock too. */ + if (mm !=3D &init_mm) + mmap_write_lock_nested(&init_mm, SINGLE_DEPTH_NESTING); + while (range->start !=3D range->end) { walk_page_range_debug(mm, range->start, range->end, &ptdump_ops, pgd, st); range++; } + + if (mm !=3D &init_mm) + mmap_write_unlock(&init_mm); mmap_write_unlock(mm); put_online_mems(); =20 --=20 2.55.0 From nobody Sat Jul 25 23:05:42 2026 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-alma10-1.taild15c8.ts.net [100.103.45.18]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 7F6D130568B; Sun, 12 Jul 2026 10:44:44 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=100.103.45.18 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783853085; cv=none; b=oNVT6TFXmaGyOWhbkWPh8xBlR5IYSgx4cm12EEZ/PwJMjLqZxO9u8U/Yxd83Om/El0biyE52boEfelCE4tMCLpwlhKYg6p0wJSpRR2YAPAiZ2TzhiERGTKr/sw6u8xSg56USGXEKKuQ939l/3fClR5o3aBzAIrqUVzSGF1WSDUw= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783853085; c=relaxed/simple; bh=GlL9IPStDd4Tw6wUpim2GluEjrJu4zbK1OV4gJFr1DI=; h=From:Date:Subject:MIME-Version:Content-Type:Message-Id:References: In-Reply-To:To:Cc; b=o2FZTzuBOn1hT9Cq7jKu++YabojkEyH69t8DgF9wNM2ZV0k6CKmUE1H2fVQEvOA8f2nXCTHoS31piG17yn0Nl5vqy44qBTLXplQy/v/zC2eG7M3dfWNptUYutp3nQJZsZM7ZTUzQvB6AzOGe1Zr8EMom/JF9B6tBtdVEVSrdT1M= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b=iHt7yzwn; arc=none smtp.client-ip=100.103.45.18 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=kernel.org header.i=@kernel.org header.b="iHt7yzwn" Received: by smtp.kernel.org (Postfix) with ESMTPSA id 7CFD01F000E9; Sun, 12 Jul 2026 10:44:37 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=kernel.org; s=k20260515; t=1783853084; bh=w3ZKkJYADp4LuVEyETZdU5oY7rqadayz5ZMLHtiQ+kM=; h=From:Date:Subject:References:In-Reply-To:To:Cc; b=iHt7yzwnmfb4E3hm94gtbrfP2oY+H4ve2xcX15Qwg0r3kIIRRm2AAgNDRanH8HfvD 26LM0AKvLNIADfJIhHJYnjRdlNVzlv9vU+n5KFEmF+8db0OeFBrQ8SI1UqCZ26Bc/G XCuMTsxDNYwvgr2xLDmJ+qmB65/ikkfLrm0dEVXkI9JmknMlj8uTTyFwqQvNKvpLYf GWAXTOTMmKtij3/MXOOVD7YvSo5napCfywpQJKM1tLFtB3KJa3AqW3yWmNWrR77QpK EcbvsF57UO4MkhdFoM9mcEs26GBO2VaJU2TGvZqlac36qmn9wTALSEMe2qFueZoq4C daqu/1hpUoi4A== From: Lorenzo Stoakes Date: Sun, 12 Jul 2026 11:42:27 +0100 Subject: [PATCH mm-hotfixes v2 4/4] arm64: remove redundant concurrent ptdump UAF mitigation Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: quoted-printable Message-Id: <20260712-series-vmap-race-fix-v2-4-ad134cc3a12a@kernel.org> References: <20260712-series-vmap-race-fix-v2-0-ad134cc3a12a@kernel.org> In-Reply-To: <20260712-series-vmap-race-fix-v2-0-ad134cc3a12a@kernel.org> To: Andrew Morton , Suren Baghdasaryan , "Liam R. Howlett" , Vlastimil Babka , Shakeel Butt , David Hildenbrand , Mike Rapoport , Michal Hocko , Uladzislau Rezki , Toshi Kani , Dave Hansen , Andy Lutomirski , Peter Zijlstra , Thomas Gleixner , Ingo Molnar , Borislav Petkov , x86@kernel.org, "H. Peter Anvin" , Kiryl Shutsemau , Catalin Marinas , Will Deacon , Dev Jain , Ryan Roberts Cc: David Carlier , ljs@kernel.org, linux-mm@kvack.org, linux-kernel@vger.kernel.org, bpf@vger.kernel.org, linux-arm-kernel@lists.infradead.org, stable@vger.kernel.org X-Mailer: b4 0.15.2 X-Developer-Signature: v=1; a=openpgp-sha256; l=6878; i=ljs@kernel.org; h=from:subject:message-id; bh=GlL9IPStDd4Tw6wUpim2GluEjrJu4zbK1OV4gJFr1DI=; b=owGbwMvMwCV2fu7ZrsZH9SKMp9WSGLKC8z9wlYVZawkyFRf3PNSLnPecf9ndfVvfBzLrfdpxn mXnlM+FHaUsDGJcDLJiiizPv4jvDxIJm9d5wd8NZg4rE8gQBi5OAZgIvwjDPwWjpackbZ8enXrQ v2wLk7GH5K2GqaaVUhESjbwePkXqeowMnR/z/wWbvLWWunvmtf3We9Li3zSPcERfCZv9+E9EfN9 8LgA= X-Developer-Key: i=ljs@kernel.org; a=openpgp; fpr=E7F417BF5214569E89D04F46CF9DCD8A81E27F14 This partially reverts commit fa93b45fd397 ("arm64: Enable vmalloc-huge with ptdump"), retaining vmalloc-huge support but eliminating the now redundant mitigation against a race between huge vmap page table freeing and ptdump, as this issue has now been fixed at core. We also simultaneously remove the arm64 if-deffery when acquiring the mmap read lock upon vmap huge page table promotion as it is no longer required. Note that this patch relies on the preceding vmalloc patch, and should not be backported alone. Fixes: fa93b45fd397 ("arm64: Enable vmalloc-huge with ptdump") Cc: stable@vger.kernel.org Reviewed-by: Dev Jain Acked-by: Mike Rapoport (Microsoft) Signed-off-by: Lorenzo Stoakes Acked-by: Kiryl Shutsemau (Meta) Acked-by: Will Deacon --- arch/arm64/include/asm/ptdump.h | 2 -- arch/arm64/mm/mmu.c | 43 ++++---------------------------------= ---- arch/arm64/mm/ptdump.c | 11 ++--------- mm/vmalloc.c | 15 +++----------- 4 files changed, 9 insertions(+), 62 deletions(-) diff --git a/arch/arm64/include/asm/ptdump.h b/arch/arm64/include/asm/ptdum= p.h index 5b374a6ab34a..50a195eda8ed 100644 --- a/arch/arm64/include/asm/ptdump.h +++ b/arch/arm64/include/asm/ptdump.h @@ -7,8 +7,6 @@ =20 #include =20 -DECLARE_STATIC_KEY_FALSE(arm64_ptdump_lock_key); - #ifdef CONFIG_PTDUMP =20 #include diff --git a/arch/arm64/mm/mmu.c b/arch/arm64/mm/mmu.c index a25d8beacc83..bd52fca6e872 100644 --- a/arch/arm64/mm/mmu.c +++ b/arch/arm64/mm/mmu.c @@ -49,8 +49,6 @@ #define NO_CONT_MAPPINGS BIT(1) #define NO_EXEC_MAPPINGS BIT(2) /* assumes FEAT_HPDS is not used */ =20 -DEFINE_STATIC_KEY_FALSE(arm64_ptdump_lock_key); - u64 kimage_voffset __ro_after_init; EXPORT_SYMBOL(kimage_voffset); =20 @@ -1864,8 +1862,7 @@ int pmd_clear_huge(pmd_t *pmdp) return 1; } =20 -static int __pmd_free_pte_page(pmd_t *pmdp, unsigned long addr, - bool acquire_mmap_lock) +int pmd_free_pte_page(pmd_t *pmdp, unsigned long addr) { pte_t *table; pmd_t pmd; @@ -1877,25 +1874,13 @@ static int __pmd_free_pte_page(pmd_t *pmdp, unsigne= d long addr, return 1; } =20 - /* See comment in pud_free_pmd_page for static key logic */ table =3D pte_offset_kernel(pmdp, addr); pmd_clear(pmdp); __flush_tlb_kernel_pgtable(addr); - if (static_branch_unlikely(&arm64_ptdump_lock_key) && acquire_mmap_lock) { - mmap_read_lock(&init_mm); - mmap_read_unlock(&init_mm); - } - pte_free_kernel(NULL, table); return 1; } =20 -int pmd_free_pte_page(pmd_t *pmdp, unsigned long addr) -{ - /* If ptdump is walking the pagetables, acquire init_mm.mmap_lock */ - return __pmd_free_pte_page(pmdp, addr, /* acquire_mmap_lock =3D */ true); -} - int pud_free_pmd_page(pud_t *pudp, unsigned long addr) { pmd_t *table; @@ -1911,36 +1896,16 @@ int pud_free_pmd_page(pud_t *pudp, unsigned long ad= dr) } =20 table =3D pmd_offset(pudp, addr); - - /* - * Our objective is to prevent ptdump from reading a PMD table which has - * been freed. In this race, if pud_free_pmd_page observes the key on - * (which got flipped by ptdump) then the mmap lock sequence here will, - * as a result of the mmap write lock/unlock sequence in ptdump, give - * us the correct synchronization. If not, this means that ptdump has - * yet not started walking the pagetables - the sequence of barriers - * issued by __flush_tlb_kernel_pgtable() guarantees that ptdump will - * observe an empty PUD. - */ - pud_clear(pudp); - __flush_tlb_kernel_pgtable(addr); - if (static_branch_unlikely(&arm64_ptdump_lock_key)) { - mmap_read_lock(&init_mm); - mmap_read_unlock(&init_mm); - } - pmdp =3D table; next =3D addr; end =3D addr + PUD_SIZE; do { if (pmd_present(pmdp_get(pmdp))) - /* - * PMD has been isolated, so ptdump won't see it. No - * need to acquire init_mm.mmap_lock. - */ - __pmd_free_pte_page(pmdp, next, /* acquire_mmap_lock =3D */ false); + pmd_free_pte_page(pmdp, next); } while (pmdp++, next +=3D PMD_SIZE, next !=3D end); =20 + pud_clear(pudp); + __flush_tlb_kernel_pgtable(addr); pmd_free(NULL, table); return 1; } diff --git a/arch/arm64/mm/ptdump.c b/arch/arm64/mm/ptdump.c index 1c20144700d7..5a76c59b5ada 100644 --- a/arch/arm64/mm/ptdump.c +++ b/arch/arm64/mm/ptdump.c @@ -283,13 +283,6 @@ void note_page_flush(struct ptdump_state *pt_st) note_page(pt_st, 0, -1, pte_val(pte_zero)); } =20 -static void arm64_ptdump_walk_pgd(struct ptdump_state *st, struct mm_struc= t *mm) -{ - static_branch_inc(&arm64_ptdump_lock_key); - ptdump_walk_pgd(st, mm, NULL); - static_branch_dec(&arm64_ptdump_lock_key); -} - void ptdump_walk(struct seq_file *s, struct ptdump_info *info) { unsigned long end =3D ~0UL; @@ -318,7 +311,7 @@ void ptdump_walk(struct seq_file *s, struct ptdump_info= *info) } }; =20 - arm64_ptdump_walk_pgd(&st.ptdump, info->mm); + ptdump_walk_pgd(&st.ptdump, info->mm, NULL); } =20 static void __init ptdump_initialize(void) @@ -360,7 +353,7 @@ bool ptdump_check_wx(void) } }; =20 - arm64_ptdump_walk_pgd(&st.ptdump, &init_mm); + ptdump_walk_pgd(&st.ptdump, &init_mm, NULL); =20 if (st.wx_pages || st.uxn_pages) { pr_warn("Checked W+X mappings: FAILED, %lu W+X pages found, %lu non-UXN = pages found\n", diff --git a/mm/vmalloc.c b/mm/vmalloc.c index 1fa9ac6e43d4..400563ac6d5d 100644 --- a/mm/vmalloc.c +++ b/mm/vmalloc.c @@ -170,10 +170,7 @@ static int vmap_try_huge_pmd(pmd_t *pmd, unsigned long= addr, unsigned long end, * Therefore, acquire the mmap read lock to prevent use-after-free when * freeing page tables. */ -#ifndef CONFIG_ARM64 - scoped_cond_guard(mmap_read_lock_try, return 0, &init_mm) -#endif - { + scoped_cond_guard(mmap_read_lock_try, return 0, &init_mm) { if (!pmd_free_pte_page(pmd, addr)) return 0; return pmd_set_huge(pmd, phys_addr, prot); @@ -230,10 +227,7 @@ static int vmap_try_huge_pud(pud_t *pud, unsigned long= addr, unsigned long end, return pud_set_huge(pud, phys_addr, prot); =20 /* See comment in vmap_try_huge_pmd(). */ -#ifndef CONFIG_ARM64 - scoped_cond_guard(mmap_read_lock_try, return 0, &init_mm) -#endif - { + scoped_cond_guard(mmap_read_lock_try, return 0, &init_mm) { if (!pud_free_pmd_page(pud, addr)) return 0; return pud_set_huge(pud, phys_addr, prot); @@ -290,10 +284,7 @@ static int vmap_try_huge_p4d(p4d_t *p4d, unsigned long= addr, unsigned long end, return p4d_set_huge(p4d, phys_addr, prot); =20 /* See comment in vmap_try_huge_pmd(). */ -#ifndef CONFIG_ARM64 - scoped_cond_guard(mmap_read_lock_try, return 0, &init_mm) -#endif - { + scoped_cond_guard(mmap_read_lock_try, return 0, &init_mm) { if (!p4d_free_pud_page(p4d, addr)) return 0; return p4d_set_huge(p4d, phys_addr, prot); --=20 2.55.0