* Re: [PATCH v2 4/4] mm/mlock: migrate folios out of CMA when mlocking a range
From: David Hildenbrand (Arm) @ 2026-07-09 10:04 UTC (permalink / raw)
To: Wandun Chen, vbabka, rostedt, mhiramat, Alexander.Krabler, hughd,
fvdl, bigeasy, linux-mm, linux-kernel, linux-trace-kernel,
linux-rt-devel
Cc: akpm, surenb, mhocko, jackmanb, hannes, ziy, ljs, riel, liam,
harry, jannh, lance.yang, mathieu.desnoyers, matthew.brost,
joshua.hahnjy, rakie.kim, byungchul, gourry, ying.huang, apopple,
pfalcato
In-Reply-To: <20260707125925.3725177-5-chenwandun1@gmail.com>
On 7/7/26 14:59, Wandun Chen wrote:
> From: Wandun Chen <chenwandun@lixiang.com>
>
> The region covered by mlock[all] may contain CMA pages. cma_alloc installs
What about ZONE_MOVABLE where memory is supposed to be migratable?
Also, what about drivers that mmap() CMA memory to user space, and
__mm_populate()->populate_vma_page_range() would actually try mlocking them, and
they actually must remain on CMA areas?
--
Cheers,
David
^ permalink raw reply
* Re: [PATCH 19/30] mm: use linear_page_[index, delta]() consistently
From: Huang, Kai @ 2026-07-09 10:07 UTC (permalink / raw)
To: ljs@kernel.org, akpm@linux-foundation.org
Cc: david@kernel.org, kvm@vger.kernel.org,
tomi.valkeinen@ideasonboard.com, dri-devel@lists.freedesktop.org,
surenb@google.com, riel@surriel.com,
linux-perf-users@vger.kernel.org, pfalcato@suse.de,
x86@kernel.org, rppt@kernel.org, jannh@google.com,
mperttunen@nvidia.com, dave.hansen@linux.intel.com,
kasan-dev@googlegroups.com, linux-trace-kernel@vger.kernel.org,
hughd@google.com, dinguyen@kernel.org, ray.huang@amd.com,
linux@armlinux.org.uk, lumag@kernel.org, tglx@kernel.org,
simona@ffwll.ch, maarten.lankhorst@linux.intel.com,
robin.clark@oss.qualcomm.com, nvdimm@lists.linux.dev,
tzimmermann@suse.de, willy@infradead.org,
linux-kernel@vger.kernel.org, patrik.r.jakobsson@gmail.com,
linux-parisc@vger.kernel.org, etnaviv@lists.freedesktop.org,
m.szyprowski@samsung.com, muchun.song@linux.dev,
abbotti@mev.co.uk, l.stach@pengutronix.de,
James.Bottomley@HansenPartnership.com, peterz@infradead.org,
christian.koenig@amd.com, mhiramat@kernel.org,
hsweeten@visionengravers.com, djbw@kernel.org,
iommu@lists.linux.dev, jarkko@kernel.org, osalvador@suse.de,
acme@kernel.org, deller@gmx.de, thierry.reding@kernel.org,
linux-arm-msm@vger.kernel.org, sj@kernel.org, pbonzini@redhat.com,
viro@zeniv.linux.org.uk, jonathanh@nvidia.com,
schuster.simon@siemens-energy.com, rostedt@goodmis.org,
mingo@redhat.com, linmiaohe@huawei.com, ankita@nvidia.com,
damon@lists.linux.dev, freedreno@lists.freedesktop.org,
brauner@kernel.org, linux-arm-kernel@lists.infradead.org,
bp@alien8.de, airlied@gmail.com, alex@shazbot.org,
liam@infradead.org, linux-tegra@vger.kernel.org, kees@kernel.org,
mripard@kernel.org, namhyung@kernel.org,
linux-sgx@vger.kernel.org, linux-fsdevel@vger.kernel.org,
oleg@redhat.com, harry@kernel.org, linux-mm@kvack.org
In-Reply-To: <bf56e2e98b512962a2fb88900d535a0e9e6769d8.1782735110.git.ljs@kernel.org>
On Mon, 2026-06-29 at 13:23 +0100, Lorenzo Stoakes wrote:
> diff --git a/arch/x86/kernel/cpu/sgx/virt.c b/arch/x86/kernel/cpu/sgx/virt.c
> index db6806c40483..6a1933ddc6fc 100644
> --- a/arch/x86/kernel/cpu/sgx/virt.c
> +++ b/arch/x86/kernel/cpu/sgx/virt.c
> @@ -9,6 +9,7 @@
> #include <linux/miscdevice.h>
> #include <linux/mm.h>
> #include <linux/mman.h>
> +#include <linux/pagemap.h>
> #include <linux/sched/mm.h>
> #include <linux/sched/signal.h>
> #include <linux/slab.h>
> @@ -41,7 +42,7 @@ static int __sgx_vepc_fault(struct sgx_vepc *vepc,
> WARN_ON(!mutex_is_locked(&vepc->lock));
>
> /* Calculate index of EPC page in virtual EPC's page_array */
> - index = vma->vm_pgoff + PFN_DOWN(addr - vma->vm_start);
> + index = linear_page_index(vma, addr);
For SGX:
Acked-by: Kai Huang <kai.huang@intel.com> # sgx
^ permalink raw reply
* Re: [PATCH v3 06/11] mm/cma: Allow dynamically creating CMA areas
From: David Hildenbrand (Arm) @ 2026-07-09 10:08 UTC (permalink / raw)
To: Marek Szyprowski, Thierry Reding, Rob Herring,
Krzysztof Kozlowski, Conor Dooley, Jonathan Hunter,
Mikko Perttunen, Yury Norov, Rasmus Villemoes, Russell King,
Alexander Gordeev, Gerald Schaefer, Heiko Carstens, Vasily Gorbik,
Christian Borntraeger, Sven Schnelle, Andrew Morton,
Lorenzo Stoakes, Liam R. Howlett, Vlastimil Babka, Mike Rapoport,
Suren Baghdasaryan, Michal Hocko, Robin Murphy, Sumit Semwal,
Benjamin Gaignard, Brian Starkey, John Stultz, T.J. Mercier,
Christian König, Steven Rostedt, Masami Hiramatsu,
Mathieu Desnoyers, Catalin Marinas, Will Deacon
Cc: devicetree, linux-tegra, linux-kernel, dri-devel, linux-media,
linux-arm-kernel, linux-s390, linux-mm, iommu, linaro-mm-sig,
linux-trace-kernel
In-Reply-To: <83e5e74d-7106-4e14-9d10-56438372f6a3@samsung.com>
On 7/9/26 07:56, Marek Szyprowski wrote:
> On 08.07.2026 10:35, David Hildenbrand (Arm) wrote:
>> On 7/7/26 12:02, Marek Szyprowski wrote:
>>>
>>> Well, the technical reason for not creating cma regions dynamically at
>>> runtime is that on some architectures (like 32bit ARM) the early fixup
>>> for the region is needed to make it functional for DMA.
>> Can you point me at the code that does that? Thanks!
> Check dma_contiguous_early_fixup() and dma_contiguous_remap() in
> arch/arm/mm/dma-mapping.c. Those functions ensures that the CPU mappings for
> the CMA reserved region in linear map are remapped with 4k pages instead
> of the 1M sections, so later, it will be possible to alter the mappings and
> change them to coherent when needed (altering 1M sections is not possible,
> because each process has it's own level-1 array even for the kernel linear
> mapping).
>
Thanks!
>
>
> However, in the use case in this patchset the reserved region is only shared
> with buddy allocator by using the CMA infrastructure, not registered to the
> regular DMA-mapping API, so it would work fine.
Yes, exactly.
> I'm not convinced that this
> is the right API to use for this though.
If it's supposed to be special DMA memory, then indeed, it would be bypassing
the DMA layer.
--
Cheers,
David
^ permalink raw reply
* Re: [PATCH v1 01/11] rcu: Rename struct rcu_gp_oldstate to rcu_gp_seq
From: Frederic Weisbecker @ 2026-07-09 11:47 UTC (permalink / raw)
To: Puranjay Mohan
Cc: rcu, linux-kernel, linux-trace-kernel, Paul E. McKenney,
Neeraj Upadhyay, Joel Fernandes, Josh Triplett, Boqun Feng,
Uladzislau Rezki, Steven Rostedt, Mathieu Desnoyers,
Lai Jiangshan, Zqiang, Masami Hiramatsu, Davidlohr Bueso,
Breno Leitao
In-Reply-To: <20260624132356.516959-2-puranjay@kernel.org>
Le Wed, Jun 24, 2026 at 06:23:43AM -0700, Puranjay Mohan a écrit :
> The polled grace-period state structure rcu_gp_oldstate holds a snapshot
> of the normal (and, on SMP, expedited) grace-period sequence numbers.
> Upcoming changes store this structure in the callback segment list, where
> the "oldstate" name reads poorly: there it represents the grace period a
> segment is waiting on and is also compared against the current
> grace-period state.
>
> Rename struct rcu_gp_oldstate to the more neutral struct rcu_gp_seq, and
> shorten its members rgos_norm and rgos_exp to norm and exp. Local
> variables and parameters of this type are renamed from rgosp/rgos to
> gsp/gs accordingly.
>
> While at it, provide a single definition of the structure in rcupdate.h
> rather than separate Tiny-RCU and Tree-RCU definitions, and give it the
> ->exp field unconditionally. Tiny RCU does not track expedited grace
> periods and leaves ->exp unused, but a single definition that always has
> ->exp lets the shared callback code in rcu_segcblist.c reference it
> without CONFIG_SMP guards, including on !SMP builds.
>
> No functional change.
>
> Signed-off-by: Puranjay Mohan <puranjay@kernel.org>
Reviewed-by: Frederic Weisbecker <frederic@kernel.org>
--
Frederic Weisbecker
SUSE Labs
^ permalink raw reply
* Re: [PATCH v2 2/4] mm/mlock: wait for migration to finish when mlocking a folio
From: Wandun @ 2026-07-09 11:50 UTC (permalink / raw)
To: Lorenzo Stoakes
Cc: vbabka, david, rostedt, mhiramat, Alexander.Krabler, hughd, fvdl,
bigeasy, linux-mm, linux-kernel, linux-trace-kernel,
linux-rt-devel, akpm, surenb, mhocko, jackmanb, hannes, ziy, riel,
liam, harry, jannh, lance.yang, mathieu.desnoyers, matthew.brost,
joshua.hahnjy, rakie.kim, byungchul, gourry, ying.huang, apopple,
pfalcato
In-Reply-To: <ak0C-DP_1ZrTVSLj@lucifer>
On 7/7/26 22:33, Lorenzo Stoakes wrote:
> On Tue, Jul 07, 2026 at 08:59:23PM +0800, Wandun Chen wrote:
>> From: Wandun Chen <chenwandun@lixiang.com>
>>
>> In RT kernels, sysctl_compact_unevictable_allowed is false by default,
>> when the mlock/mlockall system call try to lock all the present page,
>> the mlock_pte_range function skips non-present entries. If these
>> non-present entries are migration entries, and the migration is not
>> guaranteed to have completed before the mlock/mlockall, it may result
>> in a page fault on subsequent access, which then waits for the
>> migration to finish, causing spike latency in RT kernels.
>
> Is this really noticable and measurable?
Alexander Krabler reported a 1.1ms latency in [1]
https://lore.kernel.org/all/DU0PR01MB10385345F7153F334100981888259A@DU0PR01MB10385.eurprd01.prod.exchangelabs.com/
>
> I suppose not too many ranges should be mock
>
>>
>> Fix it by waiting for the migration to complete during the mlock/mlockall
>> syscall when sysctl_compact_unevictable_allowed is false.
>
> Probably better to reference the sysctl itself rather than an arbitrary varible
> name.
Got it.
>
>>
>> Fixes: 90d07210ab55 ("mm: mlock: use folios and a folio batch internally")
>
> Again I have no idea why you chose this as the fixes target, especially for
> this?
You're right, the Fixes tag was wrong.
Setting sysctl_compact_unevictable_allowed to zero was introduced in v5.7 by:
commit 6923aa0d8c62 ("mm/compaction: Disable compact_unevictable_allowed on RT")
Before this commit, mlocked page can be migrated, and dont need to wait for
migration complete.
After this commit, if don't wait for migration complete, this may result in
latency spikes.
(The batch mlock feature increases the probability of hitting migration entries.)
Will update Fixes tag in next version.
>
> But in any case, why is this separate from the previous commit? I sthis an
> entirely separate fix?
These two patches address two aspects of the same problem,
and I split them into separate patches mainly to make review easier.
Patch 1 mainly prevents pages to be migrated due to batch mlock;
patch 2 mainly ensures that pages undergoing migration have finished
migrating once the mlock system call completes.
>
>> Suggested-by: Vlastimil Babka <vbabka@suse.cz>
>> Signed-off-by: Wandun Chen <chenwandun@lixiang.com>
>> Link: https://lore.kernel.org/lkml/c8793c0f-7156-4cb7-9e6e-7909397e2fff@kernel.org/#t
>
> A nit but please strip that #t.
Got it.
>
>> ---
>> mm/mlock.c | 23 +++++++++++++++++++++--
>> 1 file changed, 21 insertions(+), 2 deletions(-)
>>
>> diff --git a/mm/mlock.c b/mm/mlock.c
>> index 97e49038d8d3..ac65de40b22b 100644
>> --- a/mm/mlock.c
>> +++ b/mm/mlock.c
>> @@ -25,6 +25,7 @@
>> #include <linux/memcontrol.h>
>> #include <linux/mm_inline.h>
>> #include <linux/secretmem.h>
>> +#include <linux/compaction.h>
>>
>> #include "internal.h"
>>
>> @@ -361,8 +362,17 @@ static int mlock_pte_range(pmd_t *pmd, unsigned long addr,
>>
>> ptl = pmd_trans_huge_lock(pmd, vma);
>> if (ptl) {
>> - if (!pmd_present(*pmd))
>> + if (!pmd_present(*pmd)) {
>> + if (unlikely((vma->vm_flags & VM_LOCKED) &&
>
> -> vma_test(vma, VMA_LOCKED_BIT)...
>
> What is the basis for your unlikely()? Don't use likely()/unlikely() just
> because it feels right. Leave them out unless you have actual profiling data to
> prove it.
>
> Remove it please.
Got it.
>
> But I'm also confused here - why are you checking for VMAs that already had
> VMA_LOCKED_BIT set when you are about to set it?
>
> Surely this shouldn't be predicated on VMA_LOCKED_BIT?
munlock also would call mlock_pte_range, if page is under undergoing migration,
munlock dont need to wait migration complete.
>
>
>> + !compaction_allow_unevictable() &&
>
> Why do we care about compaction here? Are we assuming the softleaf migration
> entry is present only for compaction reasons?
>
> So these migration entries could be there for any reason? Does it matter? Is it
> such a big deal, on mlock, to wait for migration entries? I think probably not.
>
> But then maybe some weird workload gets affected... hmm.
Indeed, there are workloads that are affected by this.
In RT kernels, RT processes typically use mlock to prevent their memory from
being swapped out, and sysctl_compact_unevictable_is set to default 0 in the
RT kernels, so mlocked memory won't be migrated and won't encounter migration
entries on access.
Using compaction_allow_unevictable here is mainly to check whether the system
is latency-sensitive. In RT kernels, sysctl_compact_unevictable_is set to 0 by
default.
If there is no waiting, the migration may won't have completed by the time of
the subsequent memory access, and then we would have to wait for migration
to finish in the page fault path. Since pmd_migration_entry_wait/migration_entry_wait
has no priority-propagation mechanism, if the process executing mlock is an
RT process, this can lead to priority inversion and latency spike occurs.
>
>> + softleaf_is_migration(softleaf_from_pmd(*pmd)))) {
>
> Use pmd_is_migration_entry()? :)
Got it.
>
> And technically you should use pmdp_get() I think? Maybe a situation where we
> don't care/need the READ_ONCE() though.
>
>> + spin_unlock(ptl);
>> + pmd_migration_entry_wait(vma->vm_mm, pmd);
>> + walk->action = ACTION_AGAIN;
>> + return 0;
>> + }
>
> This code is really disgusting, let's please not just copy/paste open-coded
> nested horror shows like this.
>
> A good rule of thumb is if you see a bunch of code 'poking out' like this and
> certainly if you copy/paste it or something very much like it, break it out into
> a function.
Got it, will do in next version.
>
> So:
>
> static bool wait_for_migration(const struct vm_area_struct *vma, softleaf_t entry)
> {
>>>>> As above I'm not sure should even be checking this?
> if (!vma_test(vma, VMA_LOCKED_BIT))
> return false;
>>>>> As above I'm not sure this makes sense?
> if (compaction_allowed_unevictable())
> return false;
>
> return softleaf_is_migration(entry);
> }
>
> Then call it like:
>
> if (ptl) {
> const pmd_t pmd = pmdp_get(pmd);
>
> if (!pmd_present(pmd)) {
> const softleaf_t entry = softleaf_from_pmd(pmd);
>
> if (!wait_for_migration(vma, entry))
> goto out;
>
> spin_unlock(ptl);
> pmd_migration_entry_wait(vma->vm_mm, pmd);
> walk->action = ACTION_AGAIN;
> return 0;
> }
> if (is_huge_zero_pmd(pmd))
> goto out;
>
> (etc. going *pmd -> pmd)
>
> But we could probably do even better than that, and assuming your dubious checks
> above aren't needed, we don't even need a helper then:
>
> if (ptl) {
> const pmd_t pmd = pmdp_get(pmd); // possibly just *pmd?
> const softleaf_t entry = softleaf_from_pmd(pmd);
>
> if (softleaf_is_migration(entry)) {
> /* Wait for migration entries. */
> spin_unlock(ptl);
> pmd_migration_entry_wait(vma->vm_mm, pmd);
> walk->action = ACTION_AGAIN;
> return 0;
> }
> if (!pmd_present(pmd))
> goto out;
> etc.
>
> And similar for the PTE stuff below.
>
> This works because softleaf_from_pmd() (and pte) will give you a 'none' softleaf
> if the entry is not a softlaf entry. So you can unconditionally call it on a
> PMD.
Got it.
>
>> goto out;
>> + }
>> if (is_huge_zero_pmd(*pmd))
>> goto out;
>> folio = pmd_folio(*pmd);
>> @@ -383,8 +393,17 @@ static int mlock_pte_range(pmd_t *pmd, unsigned long addr,
>>
>> for (pte = start_pte; addr != end; pte++, addr += PAGE_SIZE) {
>> ptent = ptep_get(pte);
>> - if (!pte_present(ptent))
>> + if (!pte_present(ptent)) {
>> + if (unlikely((vma->vm_flags & VM_LOCKED) &&
>> + !compaction_allow_unevictable() &&
>> + softleaf_is_migration(softleaf_from_pte(ptent)))) {
>> + pte_unmap_unlock(start_pte, ptl);
>> + migration_entry_wait(vma->vm_mm, pmd, addr);
>> + walk->action = ACTION_AGAIN;
>> + return 0;
>> + }
>> continue;
>> + }
>> folio = vm_normal_folio(vma, addr, ptent);
>> if (!folio || folio_is_zone_device(folio))
>> continue;
>> --
>> 2.43.0
>>
>
> Thanks, Lorenzo
Thanks again.
Wandun
^ permalink raw reply
* Re: [PATCH v1 02/11] rcu/segcblist: Add SRCU and Tasks RCU wrapper functions
From: Frederic Weisbecker @ 2026-07-09 11:51 UTC (permalink / raw)
To: Puranjay Mohan
Cc: rcu, linux-kernel, linux-trace-kernel, Paul E. McKenney,
Neeraj Upadhyay, Joel Fernandes, Josh Triplett, Boqun Feng,
Uladzislau Rezki, Steven Rostedt, Mathieu Desnoyers,
Lai Jiangshan, Zqiang, Masami Hiramatsu, Davidlohr Bueso,
Breno Leitao
In-Reply-To: <20260624132356.516959-3-puranjay@kernel.org>
Le Wed, Jun 24, 2026 at 06:23:44AM -0700, Puranjay Mohan a écrit :
> Add srcu_segcblist_advance() and srcu_segcblist_accelerate() wrappers
> that forward to the core rcu_segcblist_advance() and
> rcu_segcblist_accelerate() functions, and switch all SRCU (srcutree.c)
> and Tasks RCU (tasks.h) callers to use these wrappers.
>
> This isolates SRCU and Tasks RCU from upcoming changes to the core
> advance/accelerate functions, which will switch to struct
> rcu_gp_seq for dual normal/expedited GP tracking. Because SRCU and
> Tasks RCU use only normal GP sequences, their wrappers will maintain the
> existing unsigned long interface.
>
> No functional change.
>
> Reviewed-by: Paul E. McKenney <paulmck@kernel.org>
> Signed-off-by: Puranjay Mohan <puranjay@kernel.org>
Reviewed-by: Frederic Weisbecker <frederic@kernel.org>
--
Frederic Weisbecker
SUSE Labs
^ permalink raw reply
* Re: [PATCH] tracing: fprobe: Remove __packed from generic __fprobe_header
From: Markus Schneider-Pargmann @ 2026-07-09 12:06 UTC (permalink / raw)
To: Masami Hiramatsu, Markus Schneider-Pargmann
Cc: Steven Rostedt, Mathieu Desnoyers, Heiko Carstens, linux-kernel,
linux-trace-kernel
In-Reply-To: <20260622135659.ff84ef3b831a464b802d7c33@kernel.org>
[-- Attachment #1: Type: text/plain, Size: 2756 bytes --]
Hi Masami,
On Mon Jun 22, 2026 at 6:56 AM CEST, Masami Hiramatsu wrote:
> On Wed, 10 Jun 2026 11:20:24 +0200
> "Markus Schneider-Pargmann" <msp@baylibre.com> wrote:
>
>> Hi Masami,
>>
>> On Wed Jun 10, 2026 at 10:17 AM CEST, Masami Hiramatsu wrote:
>> > Hi Markus,
>> >
>> > Thanks for ping me.
>> >
>> > On Tue, 28 Apr 2026 10:30:29 +0200
>> > "Markus Schneider-Pargmann (The Capable Hub)" <msp@baylibre.com> wrote:
>> >
>> >> fp pointer and unsigned long have the same size on all relevant
>> >> architectures that build Linux. Furthermore this struct is only used in
>> >> architectures that do not set ARCH_DEFINE_ENCODE_FPROBE_HEADER which is
>> >> set only for 64bit architectures (apart from LoongArch).
>> >>
>> >> Both fields are aligned on these architectures so the struct with
>> >> __packed and without it are the same.
>> >>
>> >> Remove the __packed as it is unnecessary.
>> >>
>> >> Fixes: 4346ba160409 ("fprobe: Rewrite fprobe on function-graph tracer")
>> >
>> > NOTE: This is not a Fix, but just cleanup or minor update. Or, you have
>> > any problem with this __packed attribute?
>>
>> Thanks, yes it is not fixing a bug, I can remove this.
>>
>> >
>> > Unless there is no problem (or any concern), I would like to keep this
>> > as it is.
>>
>> There is currently no problem with __packed in the upstream kernel. I
>> just thought this would be a good cleanup to remove the unnecessary
>> attribute. I am working on CHERI architectures where pointers have
>> capabilities. __packed breaks these capability tags and therefore
>> doesn't work on CHERI. When looking into why this struct has a __packed
>> attribute I didn't see a reason, so I thought this would be a good patch
>> for upstream as well even though CHERI is not yet relevant for upstream
>> linux.
>
> Hi Markus,
>
> Ah, OK. CHERI makes pointers to non-long value. Are you sure
> removing __packed makes fprobe working with CHERI? If so,
> please describe it. Then I can pick it.
Sorry for the late response.
No, this patch alone doesn't make fprobe work with CHERI. __packed is
problematic for CHERI because it sets the alignment to 1 which forces
the compiler to do unaligned access operations even if the
struct/pointer is aligned. Unaligned operations do not keep the CHERI
capabilities. Without __packed the compiler knows everything is aligned
and can use aligned operations and keep the CHERI capabilities. CHERI
hardware does not support unaligned pointer capability access.
On its own it doesn't help CHERI, there are more patches that are more
CHERI specific that are needed for fprobe to work on CHERI. I just
thought it would be a great standalone patch for upstream.
Best
Markus
[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 289 bytes --]
^ permalink raw reply
* Re: [PATCH v1] tracing/remotes: Fix leak in trace_remote_alloc_buffer() error path
From: Vincent Donnefort @ 2026-07-09 12:18 UTC (permalink / raw)
To: Steven Rostedt
Cc: mhiramat, mathieu.desnoyers, linux-trace-kernel, kernel-team,
linux-kernel, Sashiko
In-Reply-To: <20260708125906.746f1def@gandalf.local.home>
On Wed, Jul 08, 2026 at 12:59:06PM -0400, Steven Rostedt wrote:
> On Wed, 8 Jul 2026 14:32:01 +0100
> Vincent Donnefort <vdonnefort@google.com> wrote:
>
> > If page allocation fails in trace_remote_alloc_buffer(), desc->nr_cpus
> > is not yet incremented for the current CPU. As a consequence, on error,
> > half-allocated rb_desc will not be freed in trace_remote_free_buffer().
> >
> > Include the failing CPU in desc->nr_cpus before going to the error path.
> >
>
> Looks like Sashiko found other issues you may want to address:
>
> https://sashiko.dev/#/patchset/20260708133201.295072-1-vdonnefort%40google.com
Yeah I saw it, the dreaded "This isn't a bug introduced by this patch" ...
Let me send a follow-up. After looking at the other issue, I think I want to
slightly modify this one actually!
>
> -- Steve
>
> > Fixes: 96e43537af54 ("tracing: Introduce trace remotes")
> > Reported-by: Sashiko <sashiko-bot@kernel.org>
> > Signed-off-by: Vincent Donnefort <vdonnefort@google.com>
> >
> > diff --git a/kernel/trace/trace_remote.c b/kernel/trace/trace_remote.c
> > index 2a6cc000ec98..62d3d431c309 100644
> > --- a/kernel/trace/trace_remote.c
> > +++ b/kernel/trace/trace_remote.c
> > @@ -1008,8 +1008,10 @@ int trace_remote_alloc_buffer(struct trace_buffer_desc *desc, size_t desc_size,
> >
> > for (id = 0; id < nr_pages; id++) {
> > rb_desc->page_va[id] = (unsigned long)__get_free_page(GFP_KERNEL);
> > - if (!rb_desc->page_va[id])
> > + if (!rb_desc->page_va[id]) {
> > + desc->nr_cpus++; /* Free this partially-allocated rb_desc */
> > goto err;
> > + }
> >
> > rb_desc->nr_page_va++;
> > }
> >
> > base-commit: 8cdeaa50eae8dad34885515f62559ee83e7e8dda
>
^ permalink raw reply
* Re: [PATCH v2 4/4] mm/mlock: migrate folios out of CMA when mlocking a range
From: Wandun @ 2026-07-09 12:25 UTC (permalink / raw)
To: Sebastian Andrzej Siewior
Cc: vbabka, david, rostedt, mhiramat, Alexander.Krabler, hughd, fvdl,
linux-mm, linux-kernel, linux-trace-kernel, linux-rt-devel, akpm,
surenb, mhocko, jackmanb, hannes, ziy, riel, liam, harry, jannh,
lance.yang, mathieu.desnoyers, matthew.brost, joshua.hahnjy,
rakie.kim, byungchul, gourry, ying.huang, apopple, pfalcato
In-Reply-To: <20260709091316.TFgtBZlE@linutronix.de>
On 7/9/26 17:13, Sebastian Andrzej Siewior wrote:
> On 2026-07-07 15:54:57 [+0100], Lorenzo Stoakes wrote:
>> On Tue, Jul 07, 2026 at 08:59:25PM +0800, Wandun Chen wrote:
>>> From: Wandun Chen <chenwandun@lixiang.com>
>>>
>>> The region covered by mlock[all] may contain CMA pages. cma_alloc installs
>>> migration entries in the page table, if a memory access occurs at this
>>> point, it must wait for the migration to complete, which may cause
>>> latency spikes on the RT kernels.
>>>
>>> Try to move the migration cost into the mlock[all] caller, which is
>>> typically a setup path. So reduce the chance of latency spikes on RT
>>> kernels by migrating the currently mapped CMA pages out of CMA region.
>>
>> 'reduce the chances of latency' so do you have any data to back this invasive
>> change or not?
>
> The application gets pages assigned which belong a CMA area. If the
> pages are in need by the CMA then those pages are replaced with other
> pages during a migration phase. Since there is no guarantee how long
> this will take and is also subject to general scheduling in the system
> it will be measurable and painful once hit.
>
>> And for RT, but nothing in here at all checks for RT? You're using this
>> compaction sysctl as an RT check somehow? That's gross.
>
> The man-page for mlock says that it guarantees to stay in RAM and/ or
> preventing to be moved to swap area. I would however argue that
> replacing physical pages in the background should fall under this since
> the application can't access them and is blocked while trying. The notes
> section (in the man-page) lists "real-time applications" and
> "deterministic timing". Therefore I think it makes sense to do this
> unconditionally for mlock areas regardless of the sysctl knob.
> Security related application probably only care that their memory does
> not hit the swap area and probably wouldn't mind 10ms delay.
Thanks for helping to explain, that helps a lot, Sebastian.
Wandun
>
>> This doesn't feel like the right solution.
>
> Sebastian
^ permalink raw reply
* Re: [PATCH v2 4/4] mm/mlock: migrate folios out of CMA when mlocking a range
From: Sebastian Andrzej Siewior @ 2026-07-09 13:15 UTC (permalink / raw)
To: David Hildenbrand (Arm)
Cc: Wandun Chen, vbabka, rostedt, mhiramat, Alexander.Krabler, hughd,
fvdl, linux-mm, linux-kernel, linux-trace-kernel, linux-rt-devel,
akpm, surenb, mhocko, jackmanb, hannes, ziy, ljs, riel, liam,
harry, jannh, lance.yang, mathieu.desnoyers, matthew.brost,
joshua.hahnjy, rakie.kim, byungchul, gourry, ying.huang, apopple,
pfalcato
In-Reply-To: <9b227263-56d9-41d5-ba8e-c969d8d68785@kernel.org>
On 2026-07-09 12:04:33 [+0200], David Hildenbrand (Arm) wrote:
> On 7/7/26 14:59, Wandun Chen wrote:
> > From: Wandun Chen <chenwandun@lixiang.com>
> >
> > The region covered by mlock[all] may contain CMA pages. cma_alloc installs
>
> What about ZONE_MOVABLE where memory is supposed to be migratable?
Would it be bad if the pages would not be movable anymore? Does this
effect just memory-hotplug or something else, too?
> Also, what about drivers that mmap() CMA memory to user space, and
> __mm_populate()->populate_vma_page_range() would actually try mlocking them, and
> they actually must remain on CMA areas?
It should be safe to skip those. They belong to device and they
shouldn't be affected by anything including getting swapped out.
Sebastian
^ permalink raw reply
* Re: [PATCH v1 03/11] rcu/segcblist: Factor out rcu_segcblist_advance_compact() helper
From: Frederic Weisbecker @ 2026-07-09 13:21 UTC (permalink / raw)
To: Puranjay Mohan
Cc: rcu, linux-kernel, linux-trace-kernel, Paul E. McKenney,
Neeraj Upadhyay, Joel Fernandes, Josh Triplett, Boqun Feng,
Uladzislau Rezki, Steven Rostedt, Mathieu Desnoyers,
Lai Jiangshan, Zqiang, Masami Hiramatsu, Davidlohr Bueso,
Breno Leitao
In-Reply-To: <20260624132356.516959-4-puranjay@kernel.org>
Le Wed, Jun 24, 2026 at 06:23:45AM -0700, Puranjay Mohan a écrit :
> This commit extracts the tail-pointer cleanup and segment compaction
> logic from rcu_segcblist_advance() into a new static helper function,
> rcu_segcblist_advance_compact(). This shared logic will be reused by the
> upcoming srcu_segcblist_advance() standalone implementation, which
> cannot call the core rcu_segcblist_advance() because that function will
> use RCU-specific globals.
>
> No functional change.
>
> Reviewed-by: Paul E. McKenney <paulmck@kernel.org>
> Signed-off-by: Puranjay Mohan <puranjay@kernel.org>
Reviewed-by: Frederic Weisbecker <frederic@kernel.org>
--
Frederic Weisbecker
SUSE Labs
^ permalink raw reply
* Re: [PATCH v1 04/11] rcu/segcblist: Track segment grace periods with struct rcu_gp_seq
From: Frederic Weisbecker @ 2026-07-09 13:33 UTC (permalink / raw)
To: Puranjay Mohan
Cc: rcu, linux-kernel, linux-trace-kernel, Paul E. McKenney,
Neeraj Upadhyay, Joel Fernandes, Josh Triplett, Boqun Feng,
Uladzislau Rezki, Steven Rostedt, Mathieu Desnoyers,
Lai Jiangshan, Zqiang, Masami Hiramatsu, Davidlohr Bueso,
Breno Leitao
In-Reply-To: <20260624132356.516959-5-puranjay@kernel.org>
Le Wed, Jun 24, 2026 at 06:23:46AM -0700, Puranjay Mohan a écrit :
> Change the type of the per-segment ->gp_seq[] array in struct
> rcu_segcblist from unsigned long to struct rcu_gp_seq. This prepares the
> callback tracking infrastructure to record both normal and expedited
> grace periods per segment.
>
> The rcu_segcblist_nextgp(), rcu_segcblist_advance(), and
> rcu_segcblist_accelerate() helpers now take a struct rcu_gp_seq * instead
> of an unsigned long, and all callers use the .norm field for comparisons
> and assignments. The SRCU and Tasks RCU wrappers construct a struct
> rcu_gp_seq with only .norm set and forward to the core helpers.
>
> No functional change: only the .norm field is used.
>
> Signed-off-by: Puranjay Mohan <puranjay@kernel.org>
Reviewed-by: Frederic Weisbecker <frederic@kernel.org>
--
Frederic Weisbecker
SUSE Labs
^ permalink raw reply
* Re: [PATCH v1 05/11] rcu: Add RCU_GET_STATE_NOT_TRACKED for subsystems without expedited GPs
From: Frederic Weisbecker @ 2026-07-09 13:48 UTC (permalink / raw)
To: Puranjay Mohan
Cc: rcu, linux-kernel, linux-trace-kernel, Paul E. McKenney,
Neeraj Upadhyay, Joel Fernandes, Josh Triplett, Boqun Feng,
Uladzislau Rezki, Steven Rostedt, Mathieu Desnoyers,
Lai Jiangshan, Zqiang, Masami Hiramatsu, Davidlohr Bueso,
Breno Leitao
In-Reply-To: <20260624132356.516959-6-puranjay@kernel.org>
Le Wed, Jun 24, 2026 at 06:23:47AM -0700, Puranjay Mohan a écrit :
> SRCU and Tasks RCU do not track expedited grace periods. When their
> callback state is checked via poll_state_synchronize_rcu_full(), the
> uninitialized or zeroed exp field could cause false-positive
> completion detection.
>
> This commit adds an RCU_GET_STATE_NOT_TRACKED sentinel value (0x2) that
> these subsystems can place into exp to indicate that expedited GP
> tracking is not applicable. The expedited sequence check in
> poll_state_synchronize_rcu_full() is guarded to skip entries marked with
> this sentinel.
>
> This is needed to allow rcu_segcblist_advance() and rcu_accelerate_cbs()
> to work with both normal and expedited grace periods via
> get_state_synchronize_rcu_full() and poll_state_synchronize_rcu_full().
>
> Reviewed-by: Paul E. McKenney <paulmck@kernel.org>
> Signed-off-by: Puranjay Mohan <puranjay@kernel.org>
Reviewed-by: Frederic Weisbecker <frederic@kernel.org>
--
Frederic Weisbecker
SUSE Labs
^ permalink raw reply
* Re: [PATCH v1 06/11] rcu: Enable RCU callbacks to benefit from expedited grace periods
From: Frederic Weisbecker @ 2026-07-09 13:58 UTC (permalink / raw)
To: Puranjay Mohan
Cc: rcu, linux-kernel, linux-trace-kernel, Paul E. McKenney,
Neeraj Upadhyay, Joel Fernandes, Josh Triplett, Boqun Feng,
Uladzislau Rezki, Steven Rostedt, Mathieu Desnoyers,
Lai Jiangshan, Zqiang, Masami Hiramatsu, Davidlohr Bueso,
Breno Leitao
In-Reply-To: <20260624132356.516959-7-puranjay@kernel.org>
Le Wed, Jun 24, 2026 at 06:23:48AM -0700, Puranjay Mohan a écrit :
> Currently, RCU callbacks only track normal grace-period sequence
> numbers. This means callbacks must wait for normal grace periods to
> complete even when expedited grace periods have already elapsed.
The changelog still misses the reason for this change. I had to read
the lwn article to understand that this matters under memory pressure
in order to release objects faster.
Thanks.
--
Frederic Weisbecker
SUSE Labs
^ permalink raw reply
* [RFC v2 0/3] arm64: kprobes: Fix single-step fault and reentry handling
From: Pu Hu @ 2026-07-09 14:22 UTC (permalink / raw)
To: mhiramat@kernel.org
Cc: ada.coupriediaz@arm.com, catalin.marinas@arm.com,
davem@davemloft.net, Hongyan Xia, Pu Hu, Jiazi Li,
linux-arm-kernel@lists.infradead.org,
linux-kernel@vger.kernel.org, linux-trace-kernel@vger.kernel.org,
naveen@kernel.org, will@kernel.org, yang@os.amperecomputing.com
From: Pu Hu <hupu@transsion.com>
This series fixes two arm64 kprobes issues observed when running
simpleperf with preemptirq tracepoints and dwarf callchains while a
kprobe is active on a frequently executed kernel function.
The crash happens in the kprobe debug exception path. While a kprobe is
preparing or executing its XOL single-step instruction, perf/trace code
can run in the same window. That code may either take a fault of its own
or hit another kprobe.
Patch 1 fixes kprobe_fault_handler() so that it only handles a fault
taken in KPROBE_HIT_SS or KPROBE_REENTER state when the faulting PC
points at the current kprobe's XOL instruction. Simulated kprobes,
which have no XOL slot at all, are filtered out at function entry so
that the normal page fault handler (including fixup_exception) can
process any fault without interference.
Patch 2 allows a kprobe hit in KPROBE_HIT_SS to be handled as a
recoverable one-level reentry, instead of treating it as unrecoverable.
This is safe because the reentry save area has not yet been consumed at
that point. Only a hit while already in KPROBE_REENTER remains
unrecoverable.
Patch 3 extends struct prev_kprobe with a saved_irqflag field so that
the outer kprobe's original DAIF state is preserved across reentry.
Without this, a nested kprobe from Patch 2 would overwrite
kcb->saved_irqflag, and the outer kprobe would restore the wrong DAIF
mask on completion, potentially leaving interrupts permanently disabled.
This follows the same logic as the existing x86 fixes:
6381c24cd6d5 ("kprobes/x86: Fix page-fault handling logic")
6a5022a56ac3 ("kprobes/x86: Allow to handle reentered kprobe on single-stepping")
v1 -> v2:
- Patch 1: moved simulated kprobe check to function entry (per
maintainer review); removed redundant xol_insn NULL check from
the inner branch.
- Patch 2: unchanged.
- Patch 3: new in v2; fixes the IRQ flag save/restore gap that
Patch 2 exposes.
- Removed the selftest patch (old Patch 3) from this series.
- Fixed Signed-off-by to use full name (Pu Hu) instead of username
(hupu).
- Updated comments and commit messages across all patches.
Reproducer:
simpleperf record -p <pid> -f 10000 \
-e preemptirq:preempt_disable \
-e preemptirq:preempt_enable \
--duration 9 --call-graph dwarf \
-o /data/local/tmp/perf.data
Before this series, the crash reproduced frequently. With all three
patches applied, it was no longer reproduced in our testing.
Pu Hu (3):
arm64: kprobes: Only handle faults originating from XOL slot
arm64: kprobes: Allow reentering kprobes while single-stepping
arm64: kprobes: Save and restore saved_irqflag in prev_kprobe
arch/arm64/include/asm/kprobes.h | 6 ++++
arch/arm64/kernel/probes/kprobes.c | 45 +++++++++++++++++++++++++++++-
2 files changed, 50 insertions(+), 1 deletion(-)
--
2.43.0
^ permalink raw reply
* [RFC v2 1/3] arm64: kprobes: Only handle faults originating from XOL slot
From: Pu Hu @ 2026-07-09 14:22 UTC (permalink / raw)
To: mhiramat@kernel.org
Cc: ada.coupriediaz@arm.com, catalin.marinas@arm.com,
davem@davemloft.net, Hongyan Xia, Pu Hu, Jiazi Li,
linux-arm-kernel@lists.infradead.org,
linux-kernel@vger.kernel.org, linux-trace-kernel@vger.kernel.org,
naveen@kernel.org, will@kernel.org, yang@os.amperecomputing.com
In-Reply-To: <20260709142215.226872-1-hupu@transsion.com>
From: Pu Hu <hupu@transsion.com>
kprobe_fault_handler() currently treats any page fault taken while in
KPROBE_HIT_SS or KPROBE_REENTER state as a kprobe single-step fault. This
assumption does not hold: perf or tracing code may run from the debug
exception path during the single-step window and take its own page fault.
When the fault is handled as a kprobe fault, the PC is rewritten to the
probe address, corrupting the exception recovery context for the real
fault. A typical reproducer is running perf with preemptirq tracepoints
and dwarf callchains while a kprobe is installed on a frequently
executed function.
Fix this in two layers:
1. At function entry, bail out immediately for simulated kprobes
(ainsn.xol_insn == NULL), since they have no XOL slot and any fault
taken during their execution cannot be a single-step fault.
2. For kprobes with an XOL slot, only handle the fault when the
faulting PC matches the XOL instruction address. Faults from any
other PC are left to the normal page fault handler.
This follows the same principle as the x86 fix in commit 6381c24cd6d5
("kprobes/x86: Fix page-fault handling logic").
Signed-off-by: Pu Hu <hupu@transsion.com>
Signed-off-by: Hongyan Xia <hongyan.xia@transsion.com>
---
arch/arm64/kernel/probes/kprobes.c | 22 ++++++++++++++++++++++
1 file changed, 22 insertions(+)
diff --git a/arch/arm64/kernel/probes/kprobes.c b/arch/arm64/kernel/probes/kprobes.c
index 43a0361a8bf0..798e4b091d1a 100644
--- a/arch/arm64/kernel/probes/kprobes.c
+++ b/arch/arm64/kernel/probes/kprobes.c
@@ -282,9 +282,31 @@ int __kprobes kprobe_fault_handler(struct pt_regs *regs, unsigned int fsr)
struct kprobe *cur = kprobe_running();
struct kprobe_ctlblk *kcb = get_kprobe_ctlblk();
+ /*
+ * Simulated kprobes execute in the debug trap context and have no
+ * XOL slot. Any page fault taken while a simulated kprobe is in
+ * progress cannot have been caused by kprobe single-stepping and
+ * must be left alone for the normal page fault handler, including
+ * fixup_exception.
+ */
+ if (cur && !cur->ainsn.xol_insn)
+ return 0;
+
switch (kcb->kprobe_status) {
case KPROBE_HIT_SS:
case KPROBE_REENTER:
+ /*
+ * A page fault taken while in KPROBE_HIT_SS or
+ * KPROBE_REENTER state is only attributable to kprobe
+ * single-stepping if the faulting PC points to the
+ * current kprobe's XOL instruction. If the fault occurred
+ * elsewhere (e.g. in perf or tracing code invoked from the
+ * debug exception path), leave it for the normal page fault
+ * handler to process.
+ */
+ if (instruction_pointer(regs) != (unsigned long)cur->ainsn.xol_insn)
+ break;
+
/*
* We are here because the instruction being single
* stepped caused a page fault. We reset the current
--
2.43.0
^ permalink raw reply related
* [RFC v2 2/3] arm64: kprobes: Allow reentering kprobes while single-stepping
From: Pu Hu @ 2026-07-09 14:22 UTC (permalink / raw)
To: mhiramat@kernel.org
Cc: ada.coupriediaz@arm.com, catalin.marinas@arm.com,
davem@davemloft.net, Hongyan Xia, Pu Hu, Jiazi Li,
linux-arm-kernel@lists.infradead.org,
linux-kernel@vger.kernel.org, linux-trace-kernel@vger.kernel.org,
naveen@kernel.org, will@kernel.org, yang@os.amperecomputing.com
In-Reply-To: <20260709142215.226872-1-hupu@transsion.com>
From: Pu Hu <hupu@transsion.com>
A kprobe can be hit while another kprobe is in KPROBE_HIT_SS state. This
can happen when tracing or perf code runs from the debug exception path
while the first kprobe is preparing or executing its out-of-line
single-step instruction.
Currently arm64 treats a kprobe hit in KPROBE_HIT_SS as unrecoverable,
the same as a hit in KPROBE_REENTER. This is too strict. A hit in
KPROBE_HIT_SS is still a one-level reentry and can be handled by saving
the current kprobe state and setting up single-step for the new probe,
just like reentry from KPROBE_HIT_ACTIVE or KPROBE_HIT_SSDONE.
The truly unrecoverable case is hitting another kprobe while already in
KPROBE_REENTER, because the reentry save area has already been consumed.
Move KPROBE_HIT_SS to the recoverable reentry cases and leave
KPROBE_REENTER as the unrecoverable nested reentry case.
This mirrors the x86 fix in commit 6a5022a56ac3
("kprobes/x86: Allow to handle reentered kprobe on single-stepping").
Signed-off-by: Pu Hu <hupu@transsion.com>
Signed-off-by: Hongyan Xia <hongyan.xia@transsion.com>
---
arch/arm64/kernel/probes/kprobes.c | 8 +++++++-
1 file changed, 7 insertions(+), 1 deletion(-)
diff --git a/arch/arm64/kernel/probes/kprobes.c b/arch/arm64/kernel/probes/kprobes.c
index 798e4b091d1a..2ca5916eca2f 100644
--- a/arch/arm64/kernel/probes/kprobes.c
+++ b/arch/arm64/kernel/probes/kprobes.c
@@ -240,10 +240,16 @@ static int __kprobes reenter_kprobe(struct kprobe *p,
switch (kcb->kprobe_status) {
case KPROBE_HIT_SSDONE:
case KPROBE_HIT_ACTIVE:
+ case KPROBE_HIT_SS:
+ /*
+ * A probe can be hit while another kprobe is preparing or
+ * executing its XOL single-step instruction. This is still a
+ * recoverable one-level reentry, so handle it in the same way as
+ * reentry from KPROBE_HIT_ACTIVE or KPROBE_HIT_SSDONE.
+ */
kprobes_inc_nmissed_count(p);
setup_singlestep(p, regs, kcb, 1);
break;
- case KPROBE_HIT_SS:
case KPROBE_REENTER:
pr_warn("Failed to recover from reentered kprobes.\n");
dump_kprobe(p);
--
2.43.0
^ permalink raw reply related
* [RFC v2 3/3] arm64: kprobes: Save and restore saved_irqflag in prev_kprobe
From: Pu Hu @ 2026-07-09 14:22 UTC (permalink / raw)
To: mhiramat@kernel.org
Cc: ada.coupriediaz@arm.com, catalin.marinas@arm.com,
davem@davemloft.net, Hongyan Xia, Pu Hu, Jiazi Li,
linux-arm-kernel@lists.infradead.org,
linux-kernel@vger.kernel.org, linux-trace-kernel@vger.kernel.org,
naveen@kernel.org, will@kernel.org, yang@os.amperecomputing.com
In-Reply-To: <20260709142215.226872-1-hupu@transsion.com>
From: Pu Hu <hupu@transsion.com>
When a kprobe is reentered from KPROBE_HIT_SS state (allowed by the
previous patch), setup_singlestep() for the nested kprobe calls
kprobes_save_local_irqflag(), overwriting kcb->saved_irqflag with the
currently masked DAIF value. The outer kprobe's original DAIF state is
lost.
When the nested kprobe completes, restore_previous_kprobe() brings back
the outer kprobe's kp and status, but saved_irqflag still contains the
nested kprobe's value. When the outer kprobe's single-step eventually
finishes, kprobes_restore_local_irqflag() applies the wrong DAIF mask,
leaving interrupts permanently disabled.
Fix this by extending struct prev_kprobe with a saved_irqflag field, and
saving/restoring it alongside kp and status. This ensures the outer
kprobe's original interrupt state is preserved across reentry.
Signed-off-by: Pu Hu <hupu@transsion.com>
Signed-off-by: Hongyan Xia <hongyan.xia@transsion.com>
---
arch/arm64/include/asm/kprobes.h | 6 ++++++
arch/arm64/kernel/probes/kprobes.c | 15 +++++++++++++++
2 files changed, 21 insertions(+)
diff --git a/arch/arm64/include/asm/kprobes.h b/arch/arm64/include/asm/kprobes.h
index f2782560647b..35ce2c94040e 100644
--- a/arch/arm64/include/asm/kprobes.h
+++ b/arch/arm64/include/asm/kprobes.h
@@ -26,6 +26,12 @@
struct prev_kprobe {
struct kprobe *kp;
unsigned int status;
+
+ /*
+ * The original DAIF state of the outer kprobe, saved here before
+ * a nested kprobe overwrites kcb->saved_irqflag during reentry.
+ */
+ unsigned long saved_irqflag;
};
/* per-cpu kprobe control block */
diff --git a/arch/arm64/kernel/probes/kprobes.c b/arch/arm64/kernel/probes/kprobes.c
index 2ca5916eca2f..4e0efad5caf2 100644
--- a/arch/arm64/kernel/probes/kprobes.c
+++ b/arch/arm64/kernel/probes/kprobes.c
@@ -174,12 +174,27 @@ static void __kprobes save_previous_kprobe(struct kprobe_ctlblk *kcb)
{
kcb->prev_kprobe.kp = kprobe_running();
kcb->prev_kprobe.status = kcb->kprobe_status;
+
+ /*
+ * Save the outer kprobe's original DAIF flags before the nested
+ * kprobe calls kprobes_save_local_irqflag() and overwrites
+ * kcb->saved_irqflag. Without this, the outer kprobe will restore
+ * the wrong DAIF state and leave interrupts permanently masked.
+ */
+ kcb->prev_kprobe.saved_irqflag = kcb->saved_irqflag;
}
static void __kprobes restore_previous_kprobe(struct kprobe_ctlblk *kcb)
{
__this_cpu_write(current_kprobe, kcb->prev_kprobe.kp);
kcb->kprobe_status = kcb->prev_kprobe.status;
+
+ /*
+ * Restore the outer kprobe's saved_irqflag so that when its
+ * single-step completes, kprobes_restore_local_irqflag() uses
+ * the correct original DAIF value.
+ */
+ kcb->saved_irqflag = kcb->prev_kprobe.saved_irqflag;
}
static void __kprobes set_current_kprobe(struct kprobe *p)
--
2.43.0
^ permalink raw reply related
* Re: [PATCH v2 1/4] mm/migrate: do not migrate folios mapped into VM_LOCKED VMAs under compaction
From: Lorenzo Stoakes @ 2026-07-09 15:00 UTC (permalink / raw)
To: Wandun
Cc: vbabka, david, rostedt, mhiramat, Alexander.Krabler, hughd, fvdl,
bigeasy, linux-mm, linux-kernel, linux-trace-kernel,
linux-rt-devel, akpm, surenb, mhocko, jackmanb, hannes, ziy, riel,
liam, harry, jannh, lance.yang, mathieu.desnoyers, matthew.brost,
joshua.hahnjy, rakie.kim, byungchul, gourry, ying.huang, apopple,
pfalcato
In-Reply-To: <f33a9dca-03d6-45f8-bd25-717b9033c75c@gmail.com>
On Thu, Jul 09, 2026 at 04:25:27PM +0800, Wandun wrote:
>
>
> On 7/7/26 21:55, Lorenzo Stoakes wrote:
> > On Tue, Jul 07, 2026 at 02:44:50PM +0100, Lorenzo Stoakes wrote:
> >> See above about deduplicating.
> >>
> >>> + ttu |= TTU_RESPECT_MLOCK;
> >>
> >> Hmm. I don't love 'respect mlock'. I guess we only know about the reason
> >> being compaction here.
> >>
> >> But I'm confused anyway. We have the folio, why aren't we just checking for
> >> PG_mlocked() here instead of getting the rmap to see if it's mapped
> >> anywhere with VMA_LOCKED_BIT?
> >
> > Also, since compaction_allow_unevictable() is a function that is accessible
> > elsewhere, you could literally just have a TTU_MIGRATION here instead and have
> > the rmap logic call compaction_allow_unevictable() instead rather than this.
> Do you mean:
> 1. change TTU_RESPECT_MLOCK to TTU_MIGRATION, that'is OK.
> 2. move call compaction_allow_unevictable() to try_to_migrate_one? but as you suggested
> migrate_mlock_allowed function, it already called compaction_allow_unevictable()
> in order to determine whether TTU_MIGRATION needs to be added. Did I misunderstand
> something somewhere?
The next paragraph addresses this.
>
> >
> > And then you could adapt the function I suggested before not to take a reason
> > parameter but rather a 'is_migration' one instead possibly and then pass (ttu &
> > TTU_MIGRATION) in.
> >
> > BUT. I still question whether this is at all needed since you have the folio you
> > can check for PG_mlocked...
>
> I described a race scenario at this link:
> https://lore.kernel.org/lkml/c372e68f-2bfc-45b6-a431-01bf55717247@gmail.com/
OK thanks. You really have to spell this out in the code in a comment, this is
really non-obvious.
I will try to look at your reply in due course (am between jobs atm).
>
>
> >
> > Cheers, Lorenzo
>
Thanks, Lorenzo
^ permalink raw reply
* Re: [PATCH 13/30] mm/vma: refactor vmg_adjust_set_range() for clarity
From: Gregory Price @ 2026-07-09 15:18 UTC (permalink / raw)
To: Lorenzo Stoakes
Cc: Andrew Morton, Russell King, Dinh Nguyen, Simon Schuster,
James E . J . Bottomley, Helge Deller, Jarkko Sakkinen,
Thomas Gleixner, Ingo Molnar, Borislav Petkov, Dave Hansen, x86,
Ian Abbott, H Hartley Sweeten, Lucas Stach, David Airlie,
Simona Vetter, Patrik Jakobsson, Maarten Lankhorst, Maxime Ripard,
Thomas Zimmermann, Rob Clark, Dmitry Baryshkov, Tomi Valkeinen,
Thierry Reding, Mikko Perttunen, Jonathan Hunter,
Christian Koenig, Huang Rui, Ankit Agrawal, Alex Williamson,
Alexander Viro, Christian Brauner, Dan Williams, Muchun Song,
Oscar Salvador, David Hildenbrand, Suren Baghdasaryan,
Liam R . Howlett, Matthew Wilcox, Marek Szyprowski,
Peter Zijlstra, Arnaldo Carvalho de Melo, Namhyung Kim,
Masami Hiramatsu, Oleg Nesterov, Steven Rostedt, SeongJae Park,
Miaohe Lin, Hugh Dickins, Mike Rapoport, Kees Cook, Paolo Bonzini,
linux-kernel, linux-arm-kernel, linux-parisc, linux-sgx, etnaviv,
dri-devel, linux-arm-msm, freedreno, linux-tegra, kvm,
linux-fsdevel, nvdimm, linux-mm, iommu, linux-perf-users,
linux-trace-kernel, kasan-dev, damon, Pedro Falcato, Rik van Riel,
Harry Yoo, Jann Horn
In-Reply-To: <ada7972f49ea7f1ff1df6d11e4651f270444f8fd.1782735110.git.ljs@kernel.org>
On Mon, Jun 29, 2026 at 01:23:24PM +0100, Lorenzo Stoakes wrote:
> Add comments with ASCII diagrams to describe what we're doing, avoid
> dubious use of PHYS_PFN(), and use vma_start_pgoff().
>
> The most complicated scenario represented here is vmg->__adjust_next_start
> - when this is set, vmg->[start, end] actually indicate the range to be
> retained, so take special care to describe this accurately.
>
> No functional change intended.
>
> Signed-off-by: Lorenzo Stoakes <ljs@kernel.org>
Reviewed-by: Gregory Price <gourry@gourry.net>
> + /*
> + * vmg->start vmg->end
> + * | |
> + * v merge v
> + * <------------->
> + * delta
> + * <------>
> + * |------|----------------|
> + * | prev | middle |
> + * |------|----------------|
> + * ^
> + * |
> + * middle->vm_start
> + */
Even with these diagrams, it's a bit difficult to understand what the
actual intent/result of this chunk is (but that may be a limitation of
me not spending enough time reading the surrounding code, not a comment
of your work here).
~Gregory
> + /*
> + * Originally:
> + *
> + * vmg->start vmg->end
> + * | |
> + * v merge v
> + * <------------>
> + * . .
> + * merge_existing_range() updates to:
> + * . .
> + * vmg->start vmg->end .
> + * | | .
> + * v retain v .
> + * <----------> .
> + * delta .
> + * <-----> .
> + * |----------------|------|
> + * | middle | next |
> + * |----------------|------|
> + * ^
> + * |
> + * next->vm_start
> + */
^ permalink raw reply
* Re: [PATCH 14/30] mm/vma: minor cleanup of expand_[upwards, downwards]()
From: Gregory Price @ 2026-07-09 15:20 UTC (permalink / raw)
To: Lorenzo Stoakes
Cc: Andrew Morton, Russell King, Dinh Nguyen, Simon Schuster,
James E . J . Bottomley, Helge Deller, Jarkko Sakkinen,
Thomas Gleixner, Ingo Molnar, Borislav Petkov, Dave Hansen, x86,
Ian Abbott, H Hartley Sweeten, Lucas Stach, David Airlie,
Simona Vetter, Patrik Jakobsson, Maarten Lankhorst, Maxime Ripard,
Thomas Zimmermann, Rob Clark, Dmitry Baryshkov, Tomi Valkeinen,
Thierry Reding, Mikko Perttunen, Jonathan Hunter,
Christian Koenig, Huang Rui, Ankit Agrawal, Alex Williamson,
Alexander Viro, Christian Brauner, Dan Williams, Muchun Song,
Oscar Salvador, David Hildenbrand, Suren Baghdasaryan,
Liam R . Howlett, Matthew Wilcox, Marek Szyprowski,
Peter Zijlstra, Arnaldo Carvalho de Melo, Namhyung Kim,
Masami Hiramatsu, Oleg Nesterov, Steven Rostedt, SeongJae Park,
Miaohe Lin, Hugh Dickins, Mike Rapoport, Kees Cook, Paolo Bonzini,
linux-kernel, linux-arm-kernel, linux-parisc, linux-sgx, etnaviv,
dri-devel, linux-arm-msm, freedreno, linux-tegra, kvm,
linux-fsdevel, nvdimm, linux-mm, iommu, linux-perf-users,
linux-trace-kernel, kasan-dev, damon, Pedro Falcato, Rik van Riel,
Harry Yoo, Jann Horn
In-Reply-To: <b24f70b72f0a9e2a37b904e5b59d80b88bd42e4a.1782735110.git.ljs@kernel.org>
On Mon, Jun 29, 2026 at 01:23:25PM +0100, Lorenzo Stoakes wrote:
> Adjust the stack expansion functions expand_upwards() and
> expand_downwards() such that they are expressed in terms of named constant
> values, and make use of vma_start_pgoff().
>
> This clearly documents that we are referencing the page offset of the start
> of the VMA.
>
> Additionally this cleans up the overflow check in expand_upwards().
>
> No functional change intended.
>
> Signed-off-by: Lorenzo Stoakes <ljs@kernel.org>
Reviewed-by: Gregory Price <gourry@gourry.net>
^ permalink raw reply
* Re: [PATCH 15/30] mm: introduce and use linear_page_delta()
From: Gregory Price @ 2026-07-09 15:22 UTC (permalink / raw)
To: Lorenzo Stoakes
Cc: Andrew Morton, Russell King, Dinh Nguyen, Simon Schuster,
James E . J . Bottomley, Helge Deller, Jarkko Sakkinen,
Thomas Gleixner, Ingo Molnar, Borislav Petkov, Dave Hansen, x86,
Ian Abbott, H Hartley Sweeten, Lucas Stach, David Airlie,
Simona Vetter, Patrik Jakobsson, Maarten Lankhorst, Maxime Ripard,
Thomas Zimmermann, Rob Clark, Dmitry Baryshkov, Tomi Valkeinen,
Thierry Reding, Mikko Perttunen, Jonathan Hunter,
Christian Koenig, Huang Rui, Ankit Agrawal, Alex Williamson,
Alexander Viro, Christian Brauner, Dan Williams, Muchun Song,
Oscar Salvador, David Hildenbrand, Suren Baghdasaryan,
Liam R . Howlett, Matthew Wilcox, Marek Szyprowski,
Peter Zijlstra, Arnaldo Carvalho de Melo, Namhyung Kim,
Masami Hiramatsu, Oleg Nesterov, Steven Rostedt, SeongJae Park,
Miaohe Lin, Hugh Dickins, Mike Rapoport, Kees Cook, Paolo Bonzini,
linux-kernel, linux-arm-kernel, linux-parisc, linux-sgx, etnaviv,
dri-devel, linux-arm-msm, freedreno, linux-tegra, kvm,
linux-fsdevel, nvdimm, linux-mm, iommu, linux-perf-users,
linux-trace-kernel, kasan-dev, damon, Pedro Falcato, Rik van Riel,
Harry Yoo, Jann Horn
In-Reply-To: <eedf589778aaab33e6df2ad6556dcde536e13460.1782735110.git.ljs@kernel.org>
On Mon, Jun 29, 2026 at 01:23:26PM +0100, Lorenzo Stoakes wrote:
> It's often useful to obtain the number of pages a given address lies at
> within a VMA.
>
> Add linear_page_delta() to determine this and update linear_page_index() to
> make use of it.
>
> Add comments to describe both linear_page_delta() and linear_page_index().
>
> No functional change intended.
>
> Signed-off-by: Lorenzo Stoakes <ljs@kernel.org>
Reviewed-by: Gregory Price <gourry@gourry.net>
^ permalink raw reply
* Re: [PATCH 16/30] mm/vma: use vma_start_pgoff(), linear_page_index() in mm code
From: Gregory Price @ 2026-07-09 15:29 UTC (permalink / raw)
To: Lorenzo Stoakes
Cc: Andrew Morton, Russell King, Dinh Nguyen, Simon Schuster,
James E . J . Bottomley, Helge Deller, Jarkko Sakkinen,
Thomas Gleixner, Ingo Molnar, Borislav Petkov, Dave Hansen, x86,
Ian Abbott, H Hartley Sweeten, Lucas Stach, David Airlie,
Simona Vetter, Patrik Jakobsson, Maarten Lankhorst, Maxime Ripard,
Thomas Zimmermann, Rob Clark, Dmitry Baryshkov, Tomi Valkeinen,
Thierry Reding, Mikko Perttunen, Jonathan Hunter,
Christian Koenig, Huang Rui, Ankit Agrawal, Alex Williamson,
Alexander Viro, Christian Brauner, Dan Williams, Muchun Song,
Oscar Salvador, David Hildenbrand, Suren Baghdasaryan,
Liam R . Howlett, Matthew Wilcox, Marek Szyprowski,
Peter Zijlstra, Arnaldo Carvalho de Melo, Namhyung Kim,
Masami Hiramatsu, Oleg Nesterov, Steven Rostedt, SeongJae Park,
Miaohe Lin, Hugh Dickins, Mike Rapoport, Kees Cook, Paolo Bonzini,
linux-kernel, linux-arm-kernel, linux-parisc, linux-sgx, etnaviv,
dri-devel, linux-arm-msm, freedreno, linux-tegra, kvm,
linux-fsdevel, nvdimm, linux-mm, iommu, linux-perf-users,
linux-trace-kernel, kasan-dev, damon, Pedro Falcato, Rik van Riel,
Harry Yoo, Jann Horn
In-Reply-To: <33d79008948391d30bab38db5ae31072ce12f0a1.1782735110.git.ljs@kernel.org>
On Mon, Jun 29, 2026 at 01:23:27PM +0100, Lorenzo Stoakes wrote:
> There are many instances in which linear_page_index() (as well as
> linear_page_delta()) is open-coded, which is confusing and inconsistent.
>
> Additionally, vma->vm_pgoff doesn't necessarily make it clear that this is
> the page offset of the start of the VMA range.
>
> Doing so also aids greppability.
>
> So use vma_start_pgoff() in favour of directly accessing vma->vm_pgoff, and
> linear_page_index() where we can.
>
> This also lays the ground for future changes which will add an anonymous
> page offset in order to be able to index MAP_PRIVATE-file backed anon
> folios in terms of their virtual page offset.
>
> No functional change intended.
>
> Signed-off-by: Lorenzo Stoakes <ljs@kernel.org>
such a nice readability improvement, thank you.
This made me wonder though whether we can make it painful for people to
open-code this in the future, otherwise I fear another one of these
patches creeping in 5-10 years down the line.
Not sure it's feasible though
Reviewed-by: Gregory Price <gourry@gourry.net>
> ---
> include/linux/huge_mm.h | 1 +
> include/linux/hugetlb.h | 3 +--
> include/linux/pagemap.h | 2 +-
> mm/damon/vaddr.c | 5 +++--
> mm/debug.c | 2 +-
> mm/filemap.c | 7 ++++---
> mm/huge_memory.c | 2 +-
> mm/hugetlb.c | 11 ++++-------
> mm/internal.h | 24 ++++++++++++++----------
> mm/khugepaged.c | 3 ++-
> mm/madvise.c | 6 +++---
> mm/mapping_dirty_helpers.c | 2 +-
> mm/memory.c | 25 +++++++++++++------------
> mm/mempolicy.c | 13 +++++++------
> mm/mremap.c | 12 ++++--------
> mm/msync.c | 4 ++--
> mm/nommu.c | 7 ++++---
> mm/pagewalk.c | 2 +-
> mm/shmem.c | 9 +++++----
> mm/userfaultfd.c | 4 ++--
> mm/util.c | 4 ++--
> mm/vma.c | 15 +++++++--------
> mm/vma_exec.c | 4 ++--
> mm/vma_init.c | 2 +-
> 24 files changed, 86 insertions(+), 83 deletions(-)
>
> diff --git a/include/linux/huge_mm.h b/include/linux/huge_mm.h
> index ad20f7f8c179..653b81d08fe7 100644
> --- a/include/linux/huge_mm.h
> +++ b/include/linux/huge_mm.h
> @@ -230,6 +230,7 @@ static inline bool thp_vma_suitable_order(struct vm_area_struct *vma,
>
> /* Don't have to check pgoff for anonymous vma */
> if (!vma_is_anonymous(vma)) {
> + /* vma_start_pgoff() in mm.h so not available. */
> if (!IS_ALIGNED((vma->vm_start >> PAGE_SHIFT) - vma->vm_pgoff,
> hpage_size >> PAGE_SHIFT))
> return false;
> diff --git a/include/linux/hugetlb.h b/include/linux/hugetlb.h
> index 2abaf99321e9..8390f50604d6 100644
> --- a/include/linux/hugetlb.h
> +++ b/include/linux/hugetlb.h
> @@ -792,8 +792,7 @@ static inline pgoff_t hugetlb_linear_page_index(struct vm_area_struct *vma,
> {
> struct hstate *h = hstate_vma(vma);
>
> - return ((address - vma->vm_start) >> huge_page_shift(h)) +
> - (vma->vm_pgoff >> huge_page_order(h));
> + return linear_page_index(vma, address) >> huge_page_order(h);
> }
>
> static inline bool order_is_gigantic(unsigned int order)
> diff --git a/include/linux/pagemap.h b/include/linux/pagemap.h
> index 644c0f25ae73..68a88d34a468 100644
> --- a/include/linux/pagemap.h
> +++ b/include/linux/pagemap.h
> @@ -1101,7 +1101,7 @@ static inline pgoff_t linear_page_index(const struct vm_area_struct *vma,
> pgoff_t pgoff;
>
> pgoff = linear_page_delta(vma, address);
> - pgoff += vma->vm_pgoff;
> + pgoff += vma_start_pgoff(vma);
> return pgoff;
> }
>
> diff --git a/mm/damon/vaddr.c b/mm/damon/vaddr.c
> index d27147603564..faa44aa3219b 100644
> --- a/mm/damon/vaddr.c
> +++ b/mm/damon/vaddr.c
> @@ -12,6 +12,7 @@
> #include <linux/mman.h>
> #include <linux/mmu_notifier.h>
> #include <linux/page_idle.h>
> +#include <linux/pagemap.h>
> #include <linux/pagewalk.h>
> #include <linux/sched/mm.h>
>
> @@ -627,8 +628,8 @@ static void damos_va_migrate_dests_add(struct folio *folio,
> }
>
> order = folio_order(folio);
> - ilx = vma->vm_pgoff >> order;
> - ilx += (addr - vma->vm_start) >> (PAGE_SHIFT + order);
> + ilx = vma_start_pgoff(vma) >> order;
> + ilx += linear_page_delta(vma, addr) >> order;
>
> for (i = 0; i < dests->nr_dests; i++)
> weight_total += dests->weight_arr[i];
> diff --git a/mm/debug.c b/mm/debug.c
> index 77fa8fe1d641..497654b36f1a 100644
> --- a/mm/debug.c
> +++ b/mm/debug.c
> @@ -163,7 +163,7 @@ void dump_vma(const struct vm_area_struct *vma)
> "flags: %#lx(%pGv)\n",
> vma, (void *)vma->vm_start, (void *)vma->vm_end, vma->vm_mm,
> (unsigned long)pgprot_val(vma->vm_page_prot),
> - vma->anon_vma, vma->vm_ops, vma->vm_pgoff,
> + vma->anon_vma, vma->vm_ops, vma_start_pgoff(vma),
> vma->vm_file, vma->vm_private_data,
> #ifdef CONFIG_PER_VMA_LOCK
> refcount_read(&vma->vm_refcnt),
> diff --git a/mm/filemap.c b/mm/filemap.c
> index 5af62e6abca5..bcb07b21a685 100644
> --- a/mm/filemap.c
> +++ b/mm/filemap.c
> @@ -3402,8 +3402,8 @@ static struct file *do_sync_mmap_readahead(struct vm_fault *vmf)
> * of memory.
> */
> struct vm_area_struct *vma = vmf->vma;
> - unsigned long start = vma->vm_pgoff;
> - unsigned long end = start + vma_pages(vma);
> + const unsigned long start = vma_start_pgoff(vma);
> + const unsigned long end = vma_end_pgoff(vma);
> unsigned long ra_end;
>
> ra->order = exec_folio_order();
> @@ -3921,7 +3921,8 @@ vm_fault_t filemap_map_pages(struct vm_fault *vmf,
> goto out;
> }
>
> - addr = vma->vm_start + ((start_pgoff - vma->vm_pgoff) << PAGE_SHIFT);
> + addr = vma->vm_start +
> + ((start_pgoff - vma_start_pgoff(vma)) << PAGE_SHIFT);
> vmf->pte = pte_offset_map_lock(vma->vm_mm, vmf->pmd, addr, &vmf->ptl);
> if (!vmf->pte) {
> folio_unlock(folio);
> diff --git a/mm/huge_memory.c b/mm/huge_memory.c
> index 2bccb0a53a0a..e94f56487225 100644
> --- a/mm/huge_memory.c
> +++ b/mm/huge_memory.c
> @@ -180,7 +180,7 @@ unsigned long __thp_vma_allowable_orders(struct vm_area_struct *vma,
> */
> if (!in_pf && shmem_file(vma->vm_file))
> return orders & shmem_allowable_huge_orders(file_inode(vma->vm_file),
> - vma, vma->vm_pgoff, 0,
> + vma, vma_start_pgoff(vma), 0,
> forced_collapse);
>
> if (!vma_is_anonymous(vma)) {
> diff --git a/mm/hugetlb.c b/mm/hugetlb.c
> index f45000149a78..d44a3ac5ee0a 100644
> --- a/mm/hugetlb.c
> +++ b/mm/hugetlb.c
> @@ -1011,8 +1011,7 @@ static long region_count(struct resv_map *resv, long f, long t)
> static pgoff_t vma_hugecache_offset(struct hstate *h,
> struct vm_area_struct *vma, unsigned long address)
> {
> - return ((address - vma->vm_start) >> huge_page_shift(h)) +
> - (vma->vm_pgoff >> huge_page_order(h));
> + return linear_page_index(vma, address) >> huge_page_order(h);
> }
>
> /*
> @@ -5372,8 +5371,7 @@ static void unmap_ref_private(struct mm_struct *mm, struct vm_area_struct *vma,
> * from page cache lookup which is in HPAGE_SIZE units.
> */
> address = address & huge_page_mask(h);
> - pgoff = ((address - vma->vm_start) >> PAGE_SHIFT) +
> - vma->vm_pgoff;
> + pgoff = linear_page_index(vma, address);
> mapping = vma->vm_file->f_mapping;
>
> /*
> @@ -6771,7 +6769,7 @@ static unsigned long page_table_shareable(struct vm_area_struct *svma,
> struct vm_area_struct *vma,
> unsigned long addr, pgoff_t idx)
> {
> - unsigned long saddr = ((idx - svma->vm_pgoff) << PAGE_SHIFT) +
> + unsigned long saddr = ((idx - vma_start_pgoff(svma)) << PAGE_SHIFT) +
> svma->vm_start;
> unsigned long sbase = saddr & PUD_MASK;
> unsigned long s_end = sbase + PUD_SIZE;
> @@ -6856,8 +6854,7 @@ pte_t *huge_pmd_share(struct mm_struct *mm, struct vm_area_struct *vma,
> unsigned long addr, pud_t *pud)
> {
> struct address_space *mapping = vma->vm_file->f_mapping;
> - pgoff_t idx = ((addr - vma->vm_start) >> PAGE_SHIFT) +
> - vma->vm_pgoff;
> + const pgoff_t idx = linear_page_index(vma, addr);
> struct vm_area_struct *svma;
> unsigned long saddr;
> pte_t *spte = NULL;
> diff --git a/mm/internal.h b/mm/internal.h
> index 181e79f1d6a2..89e5b7efe256 100644
> --- a/mm/internal.h
> +++ b/mm/internal.h
> @@ -1143,26 +1143,28 @@ static inline bool
> folio_within_range(struct folio *folio, struct vm_area_struct *vma,
> unsigned long start, unsigned long end)
> {
> - pgoff_t pgoff, addr;
> - unsigned long vma_pglen = vma_pages(vma);
> + const unsigned long vma_pglen = vma_pages(vma);
> + pgoff_t pgoff_folio, pgoff_vma_start;
> + unsigned long addr;
>
> VM_WARN_ON_FOLIO(folio_test_ksm(folio), folio);
> if (start > end)
> return false;
>
> + pgoff_folio = folio_pgoff(folio);
> + pgoff_vma_start = vma_start_pgoff(vma);
> +
> if (start < vma->vm_start)
> start = vma->vm_start;
>
> if (end > vma->vm_end)
> end = vma->vm_end;
>
> - pgoff = folio_pgoff(folio);
> -
> /* if folio start address is not in vma range */
> - if (!in_range(pgoff, vma->vm_pgoff, vma_pglen))
> + if (!in_range(pgoff_folio, pgoff_vma_start, vma_pglen))
> return false;
>
> - addr = vma->vm_start + ((pgoff - vma->vm_pgoff) << PAGE_SHIFT);
> + addr = vma->vm_start + ((pgoff_folio - pgoff_vma_start) << PAGE_SHIFT);
>
> return !(addr < start || end - addr < folio_size(folio));
> }
> @@ -1234,15 +1236,16 @@ extern pmd_t maybe_pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma);
> static inline unsigned long vma_address(const struct vm_area_struct *vma,
> pgoff_t pgoff, unsigned long nr_pages)
> {
> + const pgoff_t pgoff_start = vma_start_pgoff(vma);
> unsigned long address;
>
> - if (pgoff >= vma->vm_pgoff) {
> + if (pgoff >= pgoff_start) {
> address = vma->vm_start +
> - ((pgoff - vma->vm_pgoff) << PAGE_SHIFT);
> + ((pgoff - pgoff_start) << PAGE_SHIFT);
> /* Check for address beyond vma (or wrapped through 0?) */
> if (address < vma->vm_start || address >= vma->vm_end)
> address = -EFAULT;
> - } else if (pgoff + nr_pages - 1 >= vma->vm_pgoff) {
> + } else if (pgoff + nr_pages - 1 >= pgoff_start) {
> /* Test above avoids possibility of wrap to 0 on 32-bit */
> address = vma->vm_start;
> } else {
> @@ -1266,7 +1269,8 @@ static inline unsigned long vma_address_end(struct page_vma_mapped_walk *pvmw)
> return pvmw->address + PAGE_SIZE;
>
> pgoff = pvmw->pgoff + pvmw->nr_pages;
> - address = vma->vm_start + ((pgoff - vma->vm_pgoff) << PAGE_SHIFT);
> + address = vma->vm_start +
> + ((pgoff - vma_start_pgoff(vma)) << PAGE_SHIFT);
> /* Check for address beyond vma (or wrapped through 0?) */
> if (address < vma->vm_start || address > vma->vm_end)
> address = vma->vm_end;
> diff --git a/mm/khugepaged.c b/mm/khugepaged.c
> index bd5f86cf4bd8..ffef738d826c 100644
> --- a/mm/khugepaged.c
> +++ b/mm/khugepaged.c
> @@ -2145,7 +2145,8 @@ static void retract_page_tables(struct address_space *mapping, pgoff_t pgoff)
> spinlock_t *ptl;
> bool success = false;
>
> - addr = vma->vm_start + ((pgoff - vma->vm_pgoff) << PAGE_SHIFT);
> + addr = vma->vm_start +
> + ((pgoff - vma_start_pgoff(vma)) << PAGE_SHIFT);
> if (addr & ~HPAGE_PMD_MASK ||
> vma->vm_end < addr + HPAGE_PMD_SIZE)
> continue;
> diff --git a/mm/madvise.c b/mm/madvise.c
> index cd9bb077072c..6730c4200a93 100644
> --- a/mm/madvise.c
> +++ b/mm/madvise.c
> @@ -253,7 +253,7 @@ static void shmem_swapin_range(struct vm_area_struct *vma,
> continue;
>
> addr = vma->vm_start +
> - ((xas.xa_index - vma->vm_pgoff) << PAGE_SHIFT);
> + ((xas.xa_index - vma_start_pgoff(vma)) << PAGE_SHIFT);
> xas_pause(&xas);
> rcu_read_unlock();
>
> @@ -318,7 +318,7 @@ static long madvise_willneed(struct madvise_behavior *madv_behavior)
> mark_mmap_lock_dropped(madv_behavior);
> get_file(file);
> offset = (loff_t)(start - vma->vm_start)
> - + ((loff_t)vma->vm_pgoff << PAGE_SHIFT);
> + + ((loff_t)vma_start_pgoff(vma) << PAGE_SHIFT);
> mmap_read_unlock(mm);
> vfs_fadvise(file, offset, end - start, POSIX_FADV_WILLNEED);
> fput(file);
> @@ -1023,7 +1023,7 @@ static long madvise_remove(struct madvise_behavior *madv_behavior)
> return -EACCES;
>
> offset = (loff_t)(start - vma->vm_start)
> - + ((loff_t)vma->vm_pgoff << PAGE_SHIFT);
> + + ((loff_t)vma_start_pgoff(vma) << PAGE_SHIFT);
>
> /*
> * Filesystem's fallocate may need to take i_rwsem. We need to
> diff --git a/mm/mapping_dirty_helpers.c b/mm/mapping_dirty_helpers.c
> index 737c407f4081..e0efa36e0a07 100644
> --- a/mm/mapping_dirty_helpers.c
> +++ b/mm/mapping_dirty_helpers.c
> @@ -95,7 +95,7 @@ static int clean_record_pte(pte_t *pte, unsigned long addr,
>
> if (pte_dirty(ptent)) {
> pgoff_t pgoff = ((addr - walk->vma->vm_start) >> PAGE_SHIFT) +
> - walk->vma->vm_pgoff - cwalk->bitmap_pgoff;
> + vma_start_pgoff(walk->vma) - cwalk->bitmap_pgoff;
> pte_t old_pte = ptep_modify_prot_start(walk->vma, addr, pte);
>
> ptent = pte_mkclean(old_pte);
> diff --git a/mm/memory.c b/mm/memory.c
> index 98c1a245f45a..f5eb06544ba4 100644
> --- a/mm/memory.c
> +++ b/mm/memory.c
> @@ -725,10 +725,10 @@ static inline struct page *__vm_normal_page(struct vm_area_struct *vma,
> if (!pfn_valid(pfn))
> return NULL;
> } else {
> - unsigned long off = (addr - vma->vm_start) >> PAGE_SHIFT;
> + const pgoff_t index = linear_page_index(vma, addr);
>
> /* Only CoW'ed anon folios are "normal". */
> - if (pfn == vma->vm_pgoff + off)
> + if (pfn == index)
> return NULL;
> if (!is_cow_mapping(vma->vm_flags))
> return NULL;
> @@ -2643,7 +2643,7 @@ static int __vm_map_pages(struct vm_area_struct *vma, struct page **pages,
> int vm_map_pages(struct vm_area_struct *vma, struct page **pages,
> unsigned long num)
> {
> - return __vm_map_pages(vma, pages, num, vma->vm_pgoff);
> + return __vm_map_pages(vma, pages, num, vma_start_pgoff(vma));
> }
> EXPORT_SYMBOL(vm_map_pages);
>
> @@ -3298,7 +3298,8 @@ int vm_iomap_memory(struct vm_area_struct *vma, phys_addr_t start, unsigned long
> unsigned long pfn;
> int err;
>
> - err = __simple_ioremap_prep(vm_len, vma->vm_pgoff, start, len, &pfn);
> + err = __simple_ioremap_prep(vm_len, vma_start_pgoff(vma), start, len,
> + &pfn);
> if (err)
> return err;
>
> @@ -4342,15 +4343,15 @@ static inline void unmap_mapping_range_tree(struct address_space *mapping,
> struct zap_details *details)
> {
> struct vm_area_struct *vma;
> - unsigned long start, size;
> struct mmu_gather tlb;
>
> mapping_interval_tree_foreach(vma, mapping, first_index, last_index) {
> - const pgoff_t start_idx = max(first_index, vma->vm_pgoff);
> + const pgoff_t start_idx = max(first_index, vma_start_pgoff(vma));
> const pgoff_t end_idx = min(last_index, vma_last_pgoff(vma)) + 1;
> -
> - start = vma->vm_start + ((start_idx - vma->vm_pgoff) << PAGE_SHIFT);
> - size = (end_idx - start_idx) << PAGE_SHIFT;
> + const pgoff_t offset = start_idx - vma_start_pgoff(vma);
> + const unsigned long offset_bytes = offset << PAGE_SHIFT;
> + const unsigned long start = vma->vm_start + offset_bytes;
> + const unsigned long size = (end_idx - start_idx) << PAGE_SHIFT;
>
> tlb_gather_mmu(&tlb, vma->vm_mm);
> zap_vma_range_batched(&tlb, vma, start, size, details);
> @@ -5684,7 +5685,7 @@ vm_fault_t finish_fault(struct vm_fault *vmf)
> } else if (nr_pages > 1) {
> pgoff_t idx = folio_page_idx(folio, page);
> /* The page offset of vmf->address within the VMA. */
> - pgoff_t vma_off = vmf->pgoff - vmf->vma->vm_pgoff;
> + pgoff_t vma_off = vmf->pgoff - vma_start_pgoff(vmf->vma);
> /* The index of the entry in the pagetable for fault page. */
> pgoff_t pte_off = pte_index(vmf->address);
>
> @@ -5796,7 +5797,7 @@ static vm_fault_t do_fault_around(struct vm_fault *vmf)
> pgoff_t nr_pages = READ_ONCE(fault_around_pages);
> pgoff_t pte_off = pte_index(vmf->address);
> /* The page offset of vmf->address within the VMA. */
> - pgoff_t vma_off = vmf->pgoff - vmf->vma->vm_pgoff;
> + pgoff_t vma_off = vmf->pgoff - vma_start_pgoff(vmf->vma);
> pgoff_t from_pte, to_pte;
> vm_fault_t ret;
>
> @@ -7274,7 +7275,7 @@ void print_vma_addr(char *prefix, unsigned long ip)
> if (vma && vma->vm_file) {
> struct file *f = vma->vm_file;
> ip -= vma->vm_start;
> - ip += vma->vm_pgoff << PAGE_SHIFT;
> + ip += vma_start_pgoff(vma) << PAGE_SHIFT;
> printk("%s%pD[%lx,%lx+%lx]", prefix, f, ip,
> vma->vm_start,
> vma->vm_end - vma->vm_start);
> diff --git a/mm/mempolicy.c b/mm/mempolicy.c
> index 36699fabd3c2..650cdb23354a 100644
> --- a/mm/mempolicy.c
> +++ b/mm/mempolicy.c
> @@ -2048,8 +2048,8 @@ struct mempolicy *get_vma_policy(struct vm_area_struct *vma,
> pol = get_task_policy(current);
> if (pol->mode == MPOL_INTERLEAVE ||
> pol->mode == MPOL_WEIGHTED_INTERLEAVE) {
> - *ilx += vma->vm_pgoff >> order;
> - *ilx += (addr - vma->vm_start) >> (PAGE_SHIFT + order);
> + *ilx += vma_start_pgoff(vma) >> order;
> + *ilx += linear_page_delta(vma, addr) >> order;
> }
> return pol;
> }
> @@ -3250,16 +3250,17 @@ EXPORT_SYMBOL_FOR_MODULES(mpol_shared_policy_init, "kvm");
> int mpol_set_shared_policy(struct shared_policy *sp,
> struct vm_area_struct *vma, struct mempolicy *pol)
> {
> - int err;
> + const pgoff_t pgoff = vma_start_pgoff(vma);
> + const pgoff_t pgoff_end = vma_end_pgoff(vma);
> struct sp_node *new = NULL;
> - unsigned long sz = vma_pages(vma);
> + int err;
>
> if (pol) {
> - new = sp_alloc(vma->vm_pgoff, vma->vm_pgoff + sz, pol);
> + new = sp_alloc(pgoff, pgoff_end, pol);
> if (!new)
> return -ENOMEM;
> }
> - err = shared_policy_replace(sp, vma->vm_pgoff, vma->vm_pgoff + sz, new);
> + err = shared_policy_replace(sp, pgoff, pgoff_end, new);
> if (err && new)
> sp_free(new);
> return err;
> diff --git a/mm/mremap.c b/mm/mremap.c
> index e9c8b1d05832..079a0ba0c4a7 100644
> --- a/mm/mremap.c
> +++ b/mm/mremap.c
> @@ -948,8 +948,7 @@ static unsigned long vrm_set_new_addr(struct vma_remap_struct *vrm)
> struct vm_area_struct *vma = vrm->vma;
> unsigned long map_flags = 0;
> /* Page Offset _into_ the VMA. */
> - pgoff_t internal_pgoff = (vrm->addr - vma->vm_start) >> PAGE_SHIFT;
> - pgoff_t pgoff = vma->vm_pgoff + internal_pgoff;
> + const pgoff_t pgoff = linear_page_index(vma, vrm->addr);
> unsigned long new_addr = vrm_implies_new_addr(vrm) ? vrm->new_addr : 0;
> unsigned long res;
>
> @@ -1255,12 +1254,10 @@ static void unmap_source_vma(struct vma_remap_struct *vrm)
> static int copy_vma_and_data(struct vma_remap_struct *vrm,
> struct vm_area_struct **new_vma_ptr)
> {
> - unsigned long internal_offset = vrm->addr - vrm->vma->vm_start;
> - unsigned long internal_pgoff = internal_offset >> PAGE_SHIFT;
> - unsigned long new_pgoff = vrm->vma->vm_pgoff + internal_pgoff;
> - unsigned long moved_len;
> + const unsigned long new_pgoff = linear_page_index(vrm->vma, vrm->addr);
> struct vm_area_struct *vma = vrm->vma;
> struct vm_area_struct *new_vma;
> + unsigned long moved_len;
> int err = 0;
> PAGETABLE_MOVE(pmc, NULL, NULL, vrm->addr, vrm->new_addr, vrm->old_len);
>
> @@ -1802,8 +1799,7 @@ static int check_prep_vma(struct vma_remap_struct *vrm)
> vrm->populate_expand = true;
>
> /* Need to be careful about a growing mapping */
> - pgoff = (addr - vma->vm_start) >> PAGE_SHIFT;
> - pgoff += vma->vm_pgoff;
> + pgoff = linear_page_index(vma, addr);
> if (pgoff + (new_len >> PAGE_SHIFT) < pgoff)
> return -EINVAL;
>
> diff --git a/mm/msync.c b/mm/msync.c
> index ac4c9bfea2e7..90b491a27a14 100644
> --- a/mm/msync.c
> +++ b/mm/msync.c
> @@ -12,6 +12,7 @@
> #include <linux/mm.h>
> #include <linux/mman.h>
> #include <linux/file.h>
> +#include <linux/pagemap.h>
> #include <linux/syscalls.h>
> #include <linux/sched.h>
>
> @@ -85,8 +86,7 @@ SYSCALL_DEFINE3(msync, unsigned long, start, size_t, len, int, flags)
> goto out_unlock;
> }
> file = vma->vm_file;
> - fstart = (start - vma->vm_start) +
> - ((loff_t)vma->vm_pgoff << PAGE_SHIFT);
> + fstart = (loff_t)linear_page_index(vma, start) << PAGE_SHIFT;
> fend = fstart + (min(end, vma->vm_end) - start) - 1;
> start = vma->vm_end;
> if ((flags & MS_SYNC) && file &&
> diff --git a/mm/nommu.c b/mm/nommu.c
> index 6d168f69763f..60560b2c457e 100644
> --- a/mm/nommu.c
> +++ b/mm/nommu.c
> @@ -975,7 +975,7 @@ static int do_mmap_private(struct vm_area_struct *vma,
> /* read the contents of a file into the copy */
> loff_t fpos;
>
> - fpos = vma->vm_pgoff;
> + fpos = vma_start_pgoff(vma);
> fpos <<= PAGE_SHIFT;
>
> ret = kernel_read(vma->vm_file, base, len, &fpos);
> @@ -1355,7 +1355,8 @@ static int split_vma(struct vma_iterator *vmi, struct vm_area_struct *vma,
> delete_nommu_region(vma->vm_region);
> if (new_below) {
> vma->vm_region->vm_start = vma->vm_start = addr;
> - vma->vm_region->vm_pgoff = vma->vm_pgoff += npages;
> + vma->vm_pgoff += npages;
> + vma->vm_region->vm_pgoff = vma_start_pgoff(vma);
> } else {
> vma->vm_region->vm_end = vma->vm_end = addr;
> vma->vm_region->vm_top = addr;
> @@ -1603,7 +1604,7 @@ int vm_iomap_memory(struct vm_area_struct *vma, phys_addr_t start, unsigned long
> unsigned long pfn = start >> PAGE_SHIFT;
> unsigned long vm_len = vma->vm_end - vma->vm_start;
>
> - pfn += vma->vm_pgoff;
> + pfn += vma_start_pgoff(vma);
> return io_remap_pfn_range(vma, vma->vm_start, pfn, vm_len, vma->vm_page_prot);
> }
> EXPORT_SYMBOL(vm_iomap_memory);
> diff --git a/mm/pagewalk.c b/mm/pagewalk.c
> index 98d090ede077..0a3bbff57d46 100644
> --- a/mm/pagewalk.c
> +++ b/mm/pagewalk.c
> @@ -813,7 +813,7 @@ int walk_page_mapping(struct address_space *mapping, pgoff_t first_index,
> mapping_interval_tree_foreach(vma, mapping, first_index,
> first_index + nr - 1) {
> /* Clip to the vma */
> - vba = vma->vm_pgoff;
> + vba = vma_start_pgoff(vma);
> vea = vba + vma_pages(vma);
> cba = first_index;
> cba = max(cba, vba);
> diff --git a/mm/shmem.c b/mm/shmem.c
> index b51f83c970bb..4e7f6bc7a389 100644
> --- a/mm/shmem.c
> +++ b/mm/shmem.c
> @@ -1032,6 +1032,8 @@ unsigned long shmem_swap_usage(struct vm_area_struct *vma)
> struct inode *inode = file_inode(vma->vm_file);
> struct shmem_inode_info *info = SHMEM_I(inode);
> struct address_space *mapping = inode->i_mapping;
> + const pgoff_t pgoff = vma_start_pgoff(vma);
> + const pgoff_t pgoff_end = vma_end_pgoff(vma);
> unsigned long swapped;
>
> /* Be careful as we don't hold info->lock */
> @@ -1045,12 +1047,11 @@ unsigned long shmem_swap_usage(struct vm_area_struct *vma)
> if (!swapped)
> return 0;
>
> - if (!vma->vm_pgoff && vma->vm_end - vma->vm_start >= inode->i_size)
> + if (!pgoff && vma->vm_end - vma->vm_start >= inode->i_size)
> return swapped << PAGE_SHIFT;
>
> /* Here comes the more involved part */
> - return shmem_partial_swap_usage(mapping, vma->vm_pgoff,
> - vma->vm_pgoff + vma_pages(vma));
> + return shmem_partial_swap_usage(mapping, pgoff, pgoff_end);
> }
>
> /*
> @@ -2839,7 +2840,7 @@ static struct mempolicy *shmem_get_policy(struct vm_area_struct *vma,
> * by page order, as in shmem_get_pgoff_policy() and get_vma_policy()).
> */
> *ilx = inode->i_ino;
> - index = ((addr - vma->vm_start) >> PAGE_SHIFT) + vma->vm_pgoff;
> + index = linear_page_index(vma, addr);
> return mpol_shared_policy_lookup(&SHMEM_I(inode)->policy, index);
> }
>
> diff --git a/mm/userfaultfd.c b/mm/userfaultfd.c
> index 246af12bf801..bf4518f4449d 100644
> --- a/mm/userfaultfd.c
> +++ b/mm/userfaultfd.c
> @@ -481,7 +481,7 @@ static void mfill_retry_state_save(struct mfill_retry_state *s,
> {
> s->flags = vma_flags_and_mask(&vma->flags, MFILL_RETRY_STATE_VMA_FLAGS);
> s->ops = vma_uffd_ops(vma);
> - s->pgoff = vma->vm_pgoff;
> + s->pgoff = vma_start_pgoff(vma);
>
> if (vma->vm_file)
> s->file = get_file(vma->vm_file);
> @@ -507,7 +507,7 @@ static bool mfill_retry_state_changed(struct mfill_retry_state *state,
>
> /* VMA was file backed, but file, inode or offset has changed */
> if (!vma->vm_file || vma->vm_file->f_inode != state->file->f_inode ||
> - state->file != vma->vm_file || vma->vm_pgoff != state->pgoff)
> + state->file != vma->vm_file || vma_start_pgoff(vma) != state->pgoff)
> return true;
>
> return false;
> diff --git a/mm/util.c b/mm/util.c
> index af2c2103f0d9..61e6d32b2c16 100644
> --- a/mm/util.c
> +++ b/mm/util.c
> @@ -1188,7 +1188,7 @@ void compat_set_desc_from_vma(struct vm_area_desc *desc,
> desc->start = vma->vm_start;
> desc->end = vma->vm_end;
>
> - desc->pgoff = vma->vm_pgoff;
> + desc->pgoff = vma_start_pgoff(vma);
> desc->vm_file = vma->vm_file;
> desc->vma_flags = vma->flags;
> desc->page_prot = vma->vm_page_prot;
> @@ -1379,7 +1379,7 @@ static int call_vma_mapped(struct vm_area_struct *vma)
> if (!vm_ops || !vm_ops->mapped)
> return 0;
>
> - err = vm_ops->mapped(vma->vm_start, vma->vm_end, vma->vm_pgoff,
> + err = vm_ops->mapped(vma->vm_start, vma->vm_end, vma_start_pgoff(vma),
> vma->vm_file, &vm_private_data);
> if (err)
> return err;
> diff --git a/mm/vma.c b/mm/vma.c
> index dc4c2c1077f4..ee3a8ca13d07 100644
> --- a/mm/vma.c
> +++ b/mm/vma.c
> @@ -967,10 +967,9 @@ static __must_check struct vm_area_struct *vma_merge_existing_range(
> * prev middle next
> * extend delete delete
> */
> -
> vmg->start = prev->vm_start;
> vmg->end = next->vm_end;
> - vmg->pgoff = prev->vm_pgoff;
> + vmg->pgoff = vma_start_pgoff(prev);
>
> /*
> * We already ensured anon_vma compatibility above, so now it's
> @@ -987,9 +986,8 @@ static __must_check struct vm_area_struct *vma_merge_existing_range(
> * prev middle
> * extend shrink/delete
> */
> -
> vmg->start = prev->vm_start;
> - vmg->pgoff = prev->vm_pgoff;
> + vmg->pgoff = vma_start_pgoff(prev);
>
> if (!vmg->__remove_middle)
> vmg->__adjust_middle_start = true;
> @@ -1011,13 +1009,13 @@ static __must_check struct vm_area_struct *vma_merge_existing_range(
>
> if (vmg->__remove_middle) {
> vmg->end = next->vm_end;
> - vmg->pgoff = next->vm_pgoff - pglen;
> + vmg->pgoff = vma_start_pgoff(next) - pglen;
> } else {
> /* We shrink middle and expand next. */
> vmg->__adjust_next_start = true;
> vmg->start = middle->vm_start;
> vmg->end = start;
> - vmg->pgoff = middle->vm_pgoff;
> + vmg->pgoff = vma_start_pgoff(middle);
> }
>
> err = dup_anon_vma(next, middle, &anon_dup);
> @@ -1126,7 +1124,7 @@ struct vm_area_struct *vma_merge_new_range(struct vma_merge_struct *vmg)
> if (can_merge_left) {
> vmg->start = prev->vm_start;
> vmg->target = prev;
> - vmg->pgoff = prev->vm_pgoff;
> + vmg->pgoff = vma_start_pgoff(prev);
>
> /*
> * If this merge would result in removal of the next VMA but we
> @@ -1957,7 +1955,8 @@ struct vm_area_struct *copy_vma(struct vm_area_struct **vmap,
> VM_BUG_ON_VMA(faulted_in_anon_vma, new_vma);
> *vmap = vma = new_vma;
> }
> - *need_rmap_locks = (new_vma->vm_pgoff <= vma->vm_pgoff);
> + *need_rmap_locks =
> + (vma_start_pgoff(new_vma) <= vma_start_pgoff(vma));
> } else {
> new_vma = vm_area_dup(vma);
> if (!new_vma)
> diff --git a/mm/vma_exec.c b/mm/vma_exec.c
> index 5cee8b7efa0f..e3644a3042e2 100644
> --- a/mm/vma_exec.c
> +++ b/mm/vma_exec.c
> @@ -37,7 +37,7 @@ int relocate_vma_down(struct vm_area_struct *vma, unsigned long shift)
> unsigned long new_end = old_end - shift;
> VMA_ITERATOR(vmi, mm, new_start);
> VMG_STATE(vmg, mm, &vmi, new_start, old_end, EMPTY_VMA_FLAGS,
> - vma->vm_pgoff);
> + vma_start_pgoff(vma));
> struct vm_area_struct *next;
> struct mmu_gather tlb;
> PAGETABLE_MOVE(pmc, vma, vma, old_start, new_start, length);
> @@ -89,7 +89,7 @@ int relocate_vma_down(struct vm_area_struct *vma, unsigned long shift)
>
> vma_prev(&vmi);
> /* Shrink the vma to just the new range */
> - return vma_shrink(&vmi, vma, new_start, new_end, vma->vm_pgoff);
> + return vma_shrink(&vmi, vma, new_start, new_end, vma_start_pgoff(vma));
> }
>
> /*
> diff --git a/mm/vma_init.c b/mm/vma_init.c
> index 3c0b65950510..a459669a1654 100644
> --- a/mm/vma_init.c
> +++ b/mm/vma_init.c
> @@ -46,7 +46,7 @@ static void vm_area_init_from(const struct vm_area_struct *src,
> dest->vm_start = src->vm_start;
> dest->vm_end = src->vm_end;
> dest->anon_vma = src->anon_vma;
> - dest->vm_pgoff = src->vm_pgoff;
> + dest->vm_pgoff = vma_start_pgoff(src);
> dest->vm_file = src->vm_file;
> dest->vm_private_data = src->vm_private_data;
> vm_flags_init(dest, src->vm_flags);
> --
> 2.54.0
>
^ permalink raw reply
* Re: [PATCH v1 06/11] rcu: Enable RCU callbacks to benefit from expedited grace periods
From: Puranjay Mohan @ 2026-07-09 15:36 UTC (permalink / raw)
To: Frederic Weisbecker
Cc: rcu, linux-kernel, linux-trace-kernel, Paul E. McKenney,
Neeraj Upadhyay, Joel Fernandes, Josh Triplett, Boqun Feng,
Uladzislau Rezki, Steven Rostedt, Mathieu Desnoyers,
Lai Jiangshan, Zqiang, Masami Hiramatsu, Davidlohr Bueso,
Breno Leitao
In-Reply-To: <ak-pI2CefDoz0D0M@localhost.localdomain>
On Thu, Jul 9, 2026 at 2:59 PM Frederic Weisbecker <frederic@kernel.org> wrote:
>
> Le Wed, Jun 24, 2026 at 06:23:48AM -0700, Puranjay Mohan a écrit :
> > Currently, RCU callbacks only track normal grace-period sequence
> > numbers. This means callbacks must wait for normal grace periods to
> > complete even when expedited grace periods have already elapsed.
>
> The changelog still misses the reason for this change. I had to read
> the lwn article to understand that this matters under memory pressure
> in order to release objects faster.
>
I will update the commit message in the next version.
Thanks for your review.
^ permalink raw reply
* Re: [PATCH 17/30] mm: prefer vma_[start,end]_pgoff() to vma->vm_pgoff in kernel/
From: Gregory Price @ 2026-07-09 15:49 UTC (permalink / raw)
To: Lorenzo Stoakes
Cc: Pedro Falcato, Andrew Morton, Russell King, Dinh Nguyen,
Simon Schuster, James E . J . Bottomley, Helge Deller,
Jarkko Sakkinen, Thomas Gleixner, Ingo Molnar, Borislav Petkov,
Dave Hansen, x86, Ian Abbott, H Hartley Sweeten, Lucas Stach,
David Airlie, Simona Vetter, Patrik Jakobsson, Maarten Lankhorst,
Maxime Ripard, Thomas Zimmermann, Rob Clark, Dmitry Baryshkov,
Tomi Valkeinen, Thierry Reding, Mikko Perttunen, Jonathan Hunter,
Christian Koenig, Huang Rui, Ankit Agrawal, Alex Williamson,
Alexander Viro, Christian Brauner, Dan Williams, Muchun Song,
Oscar Salvador, David Hildenbrand, Suren Baghdasaryan,
Liam R . Howlett, Matthew Wilcox, Marek Szyprowski,
Peter Zijlstra, Arnaldo Carvalho de Melo, Namhyung Kim,
Masami Hiramatsu, Oleg Nesterov, Steven Rostedt, SeongJae Park,
Miaohe Lin, Hugh Dickins, Mike Rapoport, Kees Cook, Paolo Bonzini,
linux-kernel, linux-arm-kernel, linux-parisc, linux-sgx, etnaviv,
dri-devel, linux-arm-msm, freedreno, linux-tegra, kvm,
linux-fsdevel, nvdimm, linux-mm, iommu, linux-perf-users,
linux-trace-kernel, kasan-dev, damon, Rik van Riel, Harry Yoo,
Jann Horn
In-Reply-To: <akZGqclqQ6gS12Vv@lucifer>
On Thu, Jul 02, 2026 at 12:30:59PM +0100, Lorenzo Stoakes wrote:
>
...
> static inline unsigned long vma_offset(const struct vm_area_struct *vma,
> const unsigned long address)
> {
> /* Retains page offset and tags. */
> return address - vma->vm_start;
> }
>
...
> And I'm not sure it's really all that useful. Perhaps retaining vma_offset()
> would be though.
>
Silly question:
What's the purpose of retaining tags in a non-address value?
That sounds like there's fragility just waiting to be broken.
(I presume you are talking about things like ARM MTE and such, right?)
> This is one that I think makes more sense.
>
> But in general, I'd rather hold off from yet more churn here.
>
> I'm making these changes to establish a basis for virtual page offsets
> introduced in [0], rather than just cleaning up in general.
>
I agree with this. If the refactors here suddenly have to think about
corner cases on things like tags, that's better resolved separately.
~Gregory
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox