From: Hui Zhu <hui.zhu@linux.dev>
To: Andrew Morton <akpm@linux-foundation.org>,
David Hildenbrand <david@kernel.org>,
Lorenzo Stoakes <ljs@kernel.org>,
"Liam R. Howlett" <liam@infradead.org>,
Vlastimil Babka <vbabka@kernel.org>,
Mike Rapoport <rppt@kernel.org>,
Suren Baghdasaryan <surenb@google.com>,
Michal Hocko <mhocko@suse.com>,
linux-mm@kvack.org, linux-kernel@vger.kernel.org
Cc: Hui Zhu <zhuhui@kylinos.cn>
Subject: [PATCH v3] mm/memory: use pmdp_get_lockless() for the pmd read in do_fault_around()
Date: Tue, 3 Nov 2026 09:47:49 +0800 [thread overview]
Message-ID: <20261103014749.96764-1-hui.zhu@linux.dev> (raw)
From: Hui Zhu <zhuhui@kylinos.cn>
KCSAN reports a data-race in do_read_fault / pmd_install; the same code
is in mainline:
write (marked) to 0xffff8d52a75fb810 of 8 bytes by task 27487 on cpu 5:
native_set_pmd arch/x86/include/asm/pgtable_64.h:83 [inline]
pmd_populate arch/x86/include/asm/pgalloc.h:84 [inline]
pmd_install+0xe0/0x120 mm/memory.c:444
finish_fault+0x5bc/0xb00 mm/memory.c:5204
do_cow_fault mm/memory.c:5432 [inline]
do_fault+0x5d0/0x6e0 mm/memory.c:5526
handle_mm_fault+0x211/0x4c0 mm/memory.c:6218
__mm_populate+0x144/0x270 mm/gup.c:2207
__do_sys_mlockall+0x2cd/0x380 mm/mlock.c:764
read to 0xffff8d52a75fb810 of 8 bytes by task 27527 on cpu 9:
do_fault_around mm/memory.c:5341 [inline]
do_read_fault+0x162/0x670 mm/memory.c:5381
do_fault+0x31a/0x6e0 mm/memory.c:5524
handle_mm_fault+0x211/0x4c0 mm/memory.c:6218
faultin_page_range+0x227/0x530 mm/gup.c:2156
__x64_sys_madvise+0x67/0x80 mm/madvise.c:1479
value changed: 0x0000000000000000 -> 0x000000001386c067
Both paths only hold mmap_lock for read, so do_fault_around() tests
vmf->pmd while pmd_install() populates it under the pmd lock. The race is
benign: a stale pmd_none() only wastes the prealloc_pte, which do_fault()
frees again, and a pmd seen as populated only makes ->map_pages() find no
PTE and do_read_fault() fall back to __do_fault().
The load still has to be lockless-safe. pmdp_get() is a plain READ_ONCE()
and can tear where pmd_t is wider than a word, as on i386-PAE where
pmd_install() publishes two words with a single cmpxchg8b. Use
pmdp_get_lockless(), the accessor for pmd reads without the pmd lock and
what __pte_offset_map() already uses on this very pmd a few instructions
later. It is pmdp_get() everywhere else, so the report is silenced the
same way.
No functional change on architectures that can load a pmd in one go.
Signed-off-by: Hui Zhu <zhuhui@kylinos.cn>
---
Changelog:
v3:
Shorten the comment to one line (David Hildenbrand).
v2:
Use pmdp_get_lockless() instead of pmdp_get() (David Hildenbrand).
mm/memory.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/mm/memory.c b/mm/memory.c
index 0fb676dd2bd63..f25c2ce0ef153 100644
--- a/mm/memory.c
+++ b/mm/memory.c
@@ -6017,7 +6017,8 @@ static vm_fault_t do_fault_around(struct vm_fault *vmf)
to_pte = min3(from_pte + nr_pages, (pgoff_t)PTRS_PER_PTE,
pte_off + vma_pages(vmf->vma) - vma_off) - 1;
- if (pmd_none(*vmf->pmd)) {
+ /* pmd_install() rechecks pmd_none() under the pmd lock. */
+ if (pmd_none(pmdp_get_lockless(vmf->pmd))) {
vmf->prealloc_pte = pte_alloc_one(vmf->vma->vm_mm);
if (!vmf->prealloc_pte)
return VM_FAULT_OOM;
--
2.43.0
next reply other threads:[~2026-11-03 1:48 UTC|newest]
Thread overview: 8+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-11-03 1:47 Hui Zhu [this message]
2026-11-03 8:11 ` [PATCH v3] mm/memory: use pmdp_get_lockless() for the pmd read in do_fault_around() David Hildenbrand (Arm)
2026-11-03 9:50 ` Lorenzo Stoakes (ARM)
2026-11-03 16:15 ` David Hildenbrand (Arm)
2026-11-03 18:24 ` Lorenzo Stoakes (ARM)
2026-11-03 19:51 ` David Hildenbrand (Arm)
2026-11-03 20:27 ` Lorenzo Stoakes (ARM)
2026-11-04 9:24 ` David Hildenbrand (Arm)
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20261103014749.96764-1-hui.zhu@linux.dev \
--to=hui.zhu@linux.dev \
--cc=akpm@linux-foundation.org \
--cc=david@kernel.org \
--cc=liam@infradead.org \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-mm@kvack.org \
--cc=ljs@kernel.org \
--cc=mhocko@suse.com \
--cc=rppt@kernel.org \
--cc=surenb@google.com \
--cc=vbabka@kernel.org \
--cc=zhuhui@kylinos.cn \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.