Linux-mm Archive on lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 1/1] mm/page_table_check: widen map counters
       [not found] <cover.1784337674.git.roxy520tt@gmail.com>
@ 2026-07-18  4:27 ` Ren Wei
  2026-07-18  5:11   ` Andrew Morton
  2026-07-18  5:17   ` Matthew Wilcox
  0 siblings, 2 replies; 6+ messages in thread
From: Ren Wei @ 2026-07-18  4:27 UTC (permalink / raw)
  To: linux-mm; +Cc: pasha.tatashin, akpm, vega, roxy520tt, enjou1224z

From: Zhiling Zou <roxy520tt@gmail.com>

page_table_check_set() and page_table_check_clear() store per-page
anonymous and file map counts in signed atomic_t counters. A page can
have more than INT_MAX read-only mappings while still being mapped
legally.

The global zero page is one example: repeated read faults on private
anonymous mappings install read-only PTEs that are accounted as file
mappings. Once file_map_count wraps, the next set or clear observes a
negative count and trips BUG_ON(), allowing an unprivileged user to panic
a kernel with CONFIG_PAGE_TABLE_CHECK enabled.

Use atomic64_t for both counters so page_table_check can keep the same
type-conflict checks without overflowing at INT_MAX mappings.

Fixes: df4e817b7108 ("mm: page table check")
Cc: stable@vger.kernel.org
Reported-by: Vega <vega@nebusec.ai>
Assisted-by: Codex:gpt-5.4
Signed-off-by: Zhiling Zou <roxy520tt@gmail.com>
Reviewed-by: Ren Wei <enjou1224z@gmail.com>
---
 mm/page_table_check.c | 24 ++++++++++++------------
 1 file changed, 12 insertions(+), 12 deletions(-)

diff --git a/mm/page_table_check.c b/mm/page_table_check.c
index 53a8997ec043..edd9d9edf6fc 100644
--- a/mm/page_table_check.c
+++ b/mm/page_table_check.c
@@ -14,8 +14,8 @@
 #define pr_fmt(fmt)	"page_table_check: " fmt
 
 struct page_table_check {
-	atomic_t anon_map_count;
-	atomic_t file_map_count;
+	atomic64_t anon_map_count;
+	atomic64_t file_map_count;
 };
 
 static bool __page_table_check_enabled __initdata =
@@ -79,11 +79,11 @@ static void page_table_check_clear(unsigned long pfn, unsigned long pgcnt)
 		struct page_table_check *ptc = get_page_table_check(page_ext);
 
 		if (anon) {
-			BUG_ON(atomic_read(&ptc->file_map_count));
-			BUG_ON(atomic_dec_return(&ptc->anon_map_count) < 0);
+			BUG_ON(atomic64_read(&ptc->file_map_count));
+			BUG_ON(atomic64_dec_return(&ptc->anon_map_count) < 0);
 		} else {
-			BUG_ON(atomic_read(&ptc->anon_map_count));
-			BUG_ON(atomic_dec_return(&ptc->file_map_count) < 0);
+			BUG_ON(atomic64_read(&ptc->anon_map_count));
+			BUG_ON(atomic64_dec_return(&ptc->file_map_count) < 0);
 		}
 	}
 	rcu_read_unlock();
@@ -114,11 +114,11 @@ static void page_table_check_set(unsigned long pfn, unsigned long pgcnt,
 		struct page_table_check *ptc = get_page_table_check(page_ext);
 
 		if (anon) {
-			BUG_ON(atomic_read(&ptc->file_map_count));
-			BUG_ON(atomic_inc_return(&ptc->anon_map_count) > 1 && rw);
+			BUG_ON(atomic64_read(&ptc->file_map_count));
+			BUG_ON(atomic64_inc_return(&ptc->anon_map_count) > 1 && rw);
 		} else {
-			BUG_ON(atomic_read(&ptc->anon_map_count));
-			BUG_ON(atomic_inc_return(&ptc->file_map_count) < 0);
+			BUG_ON(atomic64_read(&ptc->anon_map_count));
+			BUG_ON(atomic64_inc_return(&ptc->file_map_count) < 0);
 		}
 	}
 	rcu_read_unlock();
@@ -139,8 +139,8 @@ void __page_table_check_zero(struct page *page, unsigned int order)
 	for_each_page_ext(page, 1 << order, page_ext, iter) {
 		struct page_table_check *ptc = get_page_table_check(page_ext);
 
-		BUG_ON(atomic_read(&ptc->anon_map_count));
-		BUG_ON(atomic_read(&ptc->file_map_count));
+		BUG_ON(atomic64_read(&ptc->anon_map_count));
+		BUG_ON(atomic64_read(&ptc->file_map_count));
 	}
 	rcu_read_unlock();
 }
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 6+ messages in thread

* Re: [PATCH 1/1] mm/page_table_check: widen map counters
  2026-07-18  4:27 ` [PATCH 1/1] mm/page_table_check: widen map counters Ren Wei
@ 2026-07-18  5:11   ` Andrew Morton
  2026-07-18  5:31     ` Andrew Morton
  2026-07-18  5:17   ` Matthew Wilcox
  1 sibling, 1 reply; 6+ messages in thread
From: Andrew Morton @ 2026-07-18  5:11 UTC (permalink / raw)
  To: Ren Wei
  Cc: linux-mm, pasha.tatashin, vega, roxy520tt, Vlastimil Babka,
	Suren Baghdasaryan, Michal Hocko, Brendan Jackman,
	Johannes Weiner

On Sat, 18 Jul 2026 12:27:20 +0800 Ren Wei <enjou1224z@gmail.com> wrote:

> From: Zhiling Zou <roxy520tt@gmail.com>
> 
> page_table_check_set() and page_table_check_clear() store per-page
> anonymous and file map counts in signed atomic_t counters. A page can
> have more than INT_MAX read-only mappings while still being mapped
> legally.
> 
> The global zero page is one example: repeated read faults on private
> anonymous mappings install read-only PTEs that are accounted as file
> mappings. Once file_map_count wraps, the next set or clear observes a
> negative count and trips BUG_ON(), allowing an unprivileged user to panic
> a kernel with CONFIG_PAGE_TABLE_CHECK enabled.
> 
> Use atomic64_t for both counters so page_table_check can keep the same
> type-conflict checks without overflowing at INT_MAX mappings.

Thanks.

> Fixes: df4e817b7108 ("mm: page table check")
> Cc: stable@vger.kernel.org
>
> ...
>
> index 53a8997ec043..edd9d9edf6fc 100644
> --- a/mm/page_table_check.c
> +++ b/mm/page_table_check.c
> @@ -14,8 +14,8 @@
>  #define pr_fmt(fmt)	"page_table_check: " fmt
>  
>  struct page_table_check {
> -	atomic_t anon_map_count;
> -	atomic_t file_map_count;
> +	atomic64_t anon_map_count;
> +	atomic64_t file_map_count;
>  };

AI review suggest this might cause problems in, of all places, page_ext.c:

	https://sashiko.dev/#/patchset/b4414b588418c52a99d959d35a40e064ae8b6e72.1784337674.git.roxy520tt@gmail.com

My googling indicates that a 64-bit atomic op on a 32-bit-aligned
address is probably usually OK, but it doesn't sound smart.

Probably adding __aligned(sizeof(atomic64_t)) will address?


^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH 1/1] mm/page_table_check: widen map counters
  2026-07-18  4:27 ` [PATCH 1/1] mm/page_table_check: widen map counters Ren Wei
  2026-07-18  5:11   ` Andrew Morton
@ 2026-07-18  5:17   ` Matthew Wilcox
  1 sibling, 0 replies; 6+ messages in thread
From: Matthew Wilcox @ 2026-07-18  5:17 UTC (permalink / raw)
  To: Ren Wei; +Cc: linux-mm, pasha.tatashin, akpm, vega, roxy520tt

On Sat, Jul 18, 2026 at 12:27:20PM +0800, Ren Wei wrote:
> page_table_check_set() and page_table_check_clear() store per-page
> anonymous and file map counts in signed atomic_t counters. A page can
> have more than INT_MAX read-only mappings while still being mapped
> legally.

No it can't.  mapcount is 32-bit.

> The global zero page is one example: repeated read faults on private

You mean "is a special case".  page_table_check should handle this
case specially.



^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH 1/1] mm/page_table_check: widen map counters
  2026-07-18  5:11   ` Andrew Morton
@ 2026-07-18  5:31     ` Andrew Morton
  2026-07-18 10:21       ` tt roxy
  0 siblings, 1 reply; 6+ messages in thread
From: Andrew Morton @ 2026-07-18  5:31 UTC (permalink / raw)
  To: Ren Wei, linux-mm, pasha.tatashin, vega, roxy520tt,
	Vlastimil Babka, Suren Baghdasaryan, Michal Hocko,
	Brendan Jackman, Johannes Weiner

On Fri, 17 Jul 2026 22:11:08 -0700 Andrew Morton <akpm@linux-foundation.org> wrote:

> Probably adding __aligned(sizeof(atomic64_t)) will address?

err, no.  I think page_ext code will need alteration for this.


^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH 1/1] mm/page_table_check: widen map counters
  2026-07-18  5:31     ` Andrew Morton
@ 2026-07-18 10:21       ` tt roxy
  2026-07-19 15:20         ` Pasha Tatashin
  0 siblings, 1 reply; 6+ messages in thread
From: tt roxy @ 2026-07-18 10:21 UTC (permalink / raw)
  To: Andrew Morton
  Cc: Ren Wei, linux-mm, pasha.tatashin, vega, Vlastimil Babka,
	Suren Baghdasaryan, Michal Hocko, Brendan Jackman,
	Johannes Weiner

On Sat, Jul 18, 2026 at 1:31 PM Andrew Morton <akpm@linux-foundation.org> wrote:
>
> On Fri, 17 Jul 2026 22:11:08 -0700 Andrew Morton <akpm@linux-foundation.org> wrote:
>
> > Probably adding __aligned(sizeof(atomic64_t)) will address?
>
> err, no.  I think page_ext code will need alteration for this.

Thanks Andrew and Matthew.

Agreed. Widening the counters is not the right direction: it changes the
page_ext storage/alignment requirements, and normal page mapcount is still
32-bit as Matthew pointed out.

I'll rework this around a zero-page-specific fix and send v2 after checking
the exact page_table_check paths.

Thanks for the review.


^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH 1/1] mm/page_table_check: widen map counters
  2026-07-18 10:21       ` tt roxy
@ 2026-07-19 15:20         ` Pasha Tatashin
  0 siblings, 0 replies; 6+ messages in thread
From: Pasha Tatashin @ 2026-07-19 15:20 UTC (permalink / raw)
  To: tt roxy
  Cc: Andrew Morton, Ren Wei, linux-mm, pasha.tatashin, vega,
	Vlastimil Babka, Suren Baghdasaryan, Michal Hocko,
	Brendan Jackman, Johannes Weiner

On 07-18 18:21, tt roxy wrote:
> On Sat, Jul 18, 2026 at 1:31 PM Andrew Morton <akpm@linux-foundation.org> wrote:
> >
> > On Fri, 17 Jul 2026 22:11:08 -0700 Andrew Morton <akpm@linux-foundation.org> wrote:
> >
> > > Probably adding __aligned(sizeof(atomic64_t)) will address?
> >
> > err, no.  I think page_ext code will need alteration for this.
> 
> Thanks Andrew and Matthew.
> 
> Agreed. Widening the counters is not the right direction: it changes the
> page_ext storage/alignment requirements, and normal page mapcount is still
> 32-bit as Matthew pointed out.

Also, double page table check overhead. So, I agree let's address the 
special case instead of widening page_ext.

Thanks,
Pasha

> 
> I'll rework this around a zero-page-specific fix and send v2 after checking
> the exact page_table_check paths.
> 
> Thanks for the review.


^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2026-07-19 15:21 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
     [not found] <cover.1784337674.git.roxy520tt@gmail.com>
2026-07-18  4:27 ` [PATCH 1/1] mm/page_table_check: widen map counters Ren Wei
2026-07-18  5:11   ` Andrew Morton
2026-07-18  5:31     ` Andrew Morton
2026-07-18 10:21       ` tt roxy
2026-07-19 15:20         ` Pasha Tatashin
2026-07-18  5:17   ` Matthew Wilcox

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox