linux/mm
Sourav Panda 7b8a8ae4dd mm/hugetlb_cma: fix null nodemask dereference in hugetlb_cma_alloc_frozen_folio
alloc_buddy_hugetlb_folio_with_mpol() can pass a NULL nodemask to
alloc_fresh_hugetlb_folio() as a fallback to allocate from all nodes.  If
order is gigantic, alloc_fresh_hugetlb_folio() propagates the NULL
nodemask down to hugetlb_cma_alloc_frozen_folio() via
alloc_gigantic_frozen_folio().

Additionally, hugetlb_cma_alloc_frozen_folio() previously attempted
allocation on hugetlb_cma[nid] without verifying if nid is included in the
caller's nodemask.  Adding a node_isset(nid, *nodemask) check ensures the
initial preferred node allocation honors the memory policy / nodemask.

However, hugetlb_cma_alloc_frozen_folio() dereferences the nodemask in
node_isset(nid, *nodemask) and for_each_node_mask(node, *nodemask),
leading to a null pointer dereference kernel panic when nodemask is NULL.

Fix this by checking if nodemask is NULL in
hugetlb_cma_alloc_frozen_folio() and defaulting it to
cpuset_current_mems_allowed.  Enclose the allocation attempts within the
cpuset seqcount retry loop so that if the cpuset changes concurrently
during allocation, the attempts are retried using the updated nodemask. 
This ensures that the initial node check and fallback loop safely honor
the task's cpuset without violating cpuset constraints or causing NULL
pointer dereferences or unexpected allocation failures.

From a userspace perspective, this bug allows an unprivileged user to
crash the kernel (trigger a panic) by requesting a gigantic hugepage
allocation with MPOL_PREFERRED_MANY on a system where CMA is only
configured on a subset of NUMA nodes.

This can be reproduced by booting a VM with two NUMA nodes, restricting
CMA to Node 1 (e.g., hugetlb_cma=1:1G default_hugepagesz=1G hugepagesz=1G
hugepages=0), and running a program that allocates a 1GB hugepage area
without reserving, restricts allocation to Node 0 using mbind() with
MPOL_PREFERRED_MANY, and triggers a page fault:

  void *ptr = mmap(NULL, 1UL << 30, PROT_READ | PROT_WRITE,
                   MAP_PRIVATE | MAP_ANONYMOUS | MAP_HUGETLB |
                   MAP_HUGE_1GB | MAP_NORESERVE, -1, 0);
  unsigned long nodemask = 1; /* Node 0 */
  mbind(ptr, 1UL << 30, MPOL_PREFERRED_MANY, &nodemask,
        sizeof(nodemask) * 8, 0);
  memset(ptr, 0, 1UL << 30); /* Trigger fault */

This results in a NULL pointer dereference:

  BUG: kernel NULL pointer dereference, address: 0000000000000000
  #PF: supervisor read access in kernel mode
  #PF: error_code(0x0000) - not-present page
  Oops: Oops: 0000 [#1] SMP NOPTI
  RIP: 0010:hugetlb_cma_alloc_frozen_folio+0x75/0x120
  Call Trace:
   <TASK>
   only_alloc_fresh_hugetlb_folio.isra.0+0x2c/0x160
   alloc_surplus_hugetlb_folio+0x6d/0x100
   alloc_hugetlb_folio+0x3c5/0x660
   hugetlb_no_page+0x3d9/0x650

Link: https://lore.kernel.org/20260811052909.475635-1-souravpanda@google.com
Fixes: eb02f14c4a ("mm/hugetlb: allow overcommitting gigantic hugepages")
Signed-off-by: Sourav Panda <souravpanda@google.com>
Reviewed-by: Muchun Song <muchun.song@linux.dev>
Reviewed-by: Anshuman Khandual <anshuman.khandual@arm.com>
Cc: David Hildenbrand <david@kernel.org>
Cc: Frank van der Linden <fvdl@google.com>
Cc: Greg Thelen <gthelen@google.com>
Cc: Johannes Weiner <hannes@cmpxchg.org>
Cc: Kefeng Wang <wangkefeng.wang@huawei.com>
Cc: Michal Hocko <mhocko@suse.com>
Cc: Oscar Salvador <osalvador@suse.de>
Cc: Rik van Riel <riel@surriel.com>
Cc: SeongJae Park <sj@kernel.org>
Cc: Shakeel Butt <shakeel.butt@linux.dev>
Cc: Suren Baghdasaryan <surenb@google.com>
Cc: Vlastimil Babka <vbabka@suse.cz>
Cc: <stable@vger.kernel.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
2026-09-01 20:26:19 -07:00
..
damon Merge branch 'mm-hotfixes-stable' into mm-stable to pick up 2026-08-24 18:40:27 -07:00
kasan kasan: fix quarantine_size accounting during cache removal 2026-08-24 18:43:21 -07:00
kfence mm/slab, kfence, memcg: completely remove obj_ext for kfence objects 2026-08-04 12:30:45 +02:00
kmsan mm: split out vmalloc declarations from internal.h 2026-08-04 19:18:46 -07:00
tests sparc/mm: export symbols for lazy_mmu_mode KUnit tests 2026-01-31 14:22:40 -08:00
alloc_tag.c alloc_tag: add accuracy based filtering to ioctl 2026-08-24 18:43:13 -07:00
arch_numa.c mm.git review status for linus..mm-stable 2026-08-27 09:17:06 -07:00
backing-dev.c mm: blk-cgroup: fix use-after-free in cgwb_release_workfn() 2026-04-18 23:24:27 -07:00
balloon.c mm: rename CONFIG_BALLOON_COMPACTION to CONFIG_BALLOON_MIGRATION 2026-01-31 14:22:36 -08:00
bpf_memcontrol.c bpf: Revert "bpf: drop KF_ACQUIRE flag on BPF kfunc bpf_get_root_mem_cgroup()" 2026-01-21 09:38:16 -08:00
cma_debug.c mm/cma_debug: fix invalid accesses for inactive CMA areas 2026-05-28 20:50:33 -07:00
cma_sysfs.c mm/cma_sysfs: skip inactive CMA areas in sysfs 2026-06-03 16:25:49 -07:00
cma.c mm/cma: remove stray newline from auto-generated CMA area name 2026-08-24 18:43:16 -07:00
cma.h mm: add some missing includes to mm-local headers 2026-08-24 18:43:03 -07:00
compaction.c mm: page_alloc: fix non-movable reclaim storm in defrag_mode 2026-08-06 18:57:24 -07:00
debug_page_alloc.c mm: debug_page_alloc: fix NULL buf in debug_guardpage_minorder_setup 2026-08-24 18:43:08 -07:00
debug_page_ref.c
debug_vm_pgtable.c mm: decouple protnone helpers from CONFIG_NUMA_BALANCING 2026-08-04 19:18:36 -07:00
debug.c mm: prefer mm->def_vma_flags in mm logic 2026-08-06 18:57:02 -07:00
dmapool_test.c Convert 'alloc_obj' family to use the new default GFP_KERNEL argument 2026-02-21 17:09:51 -08:00
dmapool.c
early_ioremap.c mm/early_ioremap: clarify early_ioremap_reset() semantics 2026-08-06 18:57:21 -07:00
execmem.c mm: split out vmalloc declarations from internal.h 2026-08-04 19:18:46 -07:00
fadvise.c mm/fadvise: validate offset in generic_fadvise 2026-04-05 13:52:53 -07:00
fail_page_alloc.c
failslab.c
filemap.c Merge branch 'mm-hotfixes-stable' into mm-stable to pick up 2026-08-24 18:40:27 -07:00
folio-compat.c mm/page-writeback: document folio_mark_dirty() locking more explicitly 2026-08-24 18:43:19 -07:00
folio.c memcg: move LRU size accounting on reparenting instead of copying it 2026-08-24 18:43:33 -07:00
gup_test.c mm/gup_test: keep longterm pin state per file 2026-08-24 18:43:17 -07:00
gup_test.h
gup.c mm/gup: factor out LRU cache draining for folio into lru_cache_drain_for_folio() 2026-08-24 18:43:00 -07:00
highmem.c mm/highmem: fix __kmap_to_page() build error 2026-01-31 14:22:38 -08:00
hmm.c mm/hmm.c:hmm_do_fault(): suppress sparse warning 2026-08-24 18:43:24 -07:00
huge_memory.c mm/huge_memory: use folio's memcg inside __folio_split() 2026-08-24 18:42:59 -07:00
hugetlb_cgroup.c Convert 'alloc_flex' family to use the new default GFP_KERNEL argument 2026-02-21 17:09:51 -08:00
hugetlb_cma.c mm/hugetlb_cma: fix null nodemask dereference in hugetlb_cma_alloc_frozen_folio 2026-09-01 20:26:19 -07:00
hugetlb_cma.h mm: add some missing includes to mm-local headers 2026-08-24 18:43:03 -07:00
hugetlb_internal.h
hugetlb_sysctl.c mm, hugetlb: implement movable_gigantic_pages sysctl 2026-01-20 19:24:50 -08:00
hugetlb_sysfs.c
hugetlb_vmemmap.c mm/hugetlb_vmemmap: remove bootmem_info leftovers 2026-08-04 19:18:42 -07:00
hugetlb_vmemmap.h mm/sparse-vmemmap: remove sparse_vmemmap_init_nid_late() 2026-07-28 21:12:00 -07:00
hugetlb.c mm.git review status for linus..mm-stable 2026-08-27 09:17:06 -07:00
hwpoison-inject.c
init-mm.c exec_state: relocate dumpable information 2026-05-26 11:02:01 +02:00
internal.h mm/gup: factor out LRU cache draining for folio into lru_cache_drain_for_folio() 2026-08-24 18:43:00 -07:00
interval_tree.c mm/rmap: use anon pgoff to track MAP_PRIVATE file-backed anon folios 2026-08-24 18:42:53 -07:00
ioremap.c
Kconfig mm/Kconfig: make MEMORY_FAILURE select MIGRATION 2026-08-24 18:43:24 -07:00
Kconfig.debug percpu: drop CONFIG_DEBUG_FORCE_WEAK_PER_CPU 2026-08-24 18:43:24 -07:00
khugepaged.c mm/khugepaged: unmap pte before releasing vma write lock 2026-08-24 18:43:23 -07:00
kmemleak.c mm: kmemleak: default min_unref_scans to 2 for verbose auto-scan 2026-08-24 18:43:18 -07:00
ksm.c ksm: update comments and docs to reference folio->mapping 2026-08-24 18:43:02 -07:00
list_lru.c mm.git review status for mm-hotfixes-stable..mm-stable 2026-06-19 10:14:34 -07:00
maccess.c
madvise.c mm.git review status for linus..mm-stable 2026-08-27 09:17:06 -07:00
Makefile drivers/base, mm: move arch_numa.c to mm/ 2026-08-24 18:43:10 -07:00
mapping_dirty_helpers.c mm/vma: use vma_start_pgoff(), linear_page_index() in mm code 2026-08-04 19:19:00 -07:00
memblock.c kho: make boot time huge page allocation work nicely with KHO 2026-08-23 09:17:38 -07:00
memcontrol-v1.c mm/vmscan: reduce lru_lock contention via vmstat-derived scan-balance cost 2026-08-24 18:42:56 -07:00
memcontrol-v1.h mm: add some missing includes to mm-local headers 2026-08-24 18:43:03 -07:00
memcontrol.c mm.git review status for linus..mm-stable 2026-08-27 09:17:06 -07:00
memfd_luo.c mm/memfd_luo: document preservation of file seals 2026-05-04 14:03:16 +00:00
memfd.c mm/vma: update do_mmap() to use vma_flags_t 2026-08-06 18:57:01 -07:00
memory_hotplug.c mm/memory_hotplug: add offline_and_remove_memory_ranges() 2026-08-06 18:56:59 -07:00
memory-failure.c mm: introduce and use vma_filebacked_address() 2026-08-24 18:42:51 -07:00
memory-tiers.c mm: introduce CONFIG_NUMA_MIGRATION and simplify CONFIG_MIGRATION 2026-04-05 13:53:33 -07:00
memory.c mm.git review status for linus..mm-stable 2026-08-27 09:17:06 -07:00
mempolicy.c mm: provide vma_[flags_]is_cow_mapping() and remove is_cow_mapping() 2026-08-24 18:42:50 -07:00
mempool.c mm/mempool: Untangle CONFIG_SLUB_DEBUG_ON abuse and switch to static key 2026-07-08 18:31:27 +02:00
memremap.c mm: decrement MTHP_STAT_NR_ANON in free_zone_device_folio() 2026-07-28 17:37:31 -07:00
memtest.c
migrate_device.c mm/migrate_device: fix cache flush when replacing huge zero PMD 2026-08-24 18:43:26 -07:00
migrate.c mm/migrate: calculate large folio page index using PFN 2026-08-24 18:42:53 -07:00
mincore.c mm: mincore: refactor mincore_page() 2026-08-06 18:57:15 -07:00
mlock.c mm/mlock: convert mlock code to use vma_flags_t 2026-08-06 18:57:03 -07:00
mm_init.c mm.git review status for linus..mm-stable 2026-08-27 09:17:06 -07:00
mm_init.h mm: split out mm_init and memblock declarations from internal.h 2026-08-04 19:18:45 -07:00
mm_slot.h mm/mm_slot.h: add comments for mm_slot_lookup/insert 2026-08-06 18:57:04 -07:00
mmap_lock.c mm/vma: improve and document __is_vma_write_locked() 2026-01-31 14:22:51 -08:00
mmap.c mm/vma: convert miscellaneous uses of VMA flags in core mm 2026-08-06 18:57:03 -07:00
mmu_gather.c mm/mmu_gather: replace IPI with synchronize_rcu() when batch allocation fails 2026-04-05 13:53:05 -07:00
mmu_notifier.c mm/vma: correct incorrect vma.h inclusion 2026-08-04 19:19:04 -07:00
mmzone.c mm/vmscan: reduce lru_lock contention via vmstat-derived scan-balance cost 2026-08-24 18:42:56 -07:00
mprotect.c mm/mprotect: convert mprotect code to use vma_flags_t 2026-08-06 18:57:04 -07:00
mremap.c mm: use proper PTE accessor in move_ptes() 2026-08-24 18:42:58 -07:00
mseal.c mm/mseal: remove further superfluous comments, do_mseal() 2026-08-06 18:57:12 -07:00
msync.c mm/vma: use vma_start_pgoff(), linear_page_index() in mm code 2026-08-04 19:19:00 -07:00
nommu.c mm: nommu: point to the write iterator upon split_vma 2026-08-24 18:42:48 -07:00
numa_emulation.c mm/fake-numa: fix under-allocation detection in uniform split 2026-06-02 08:34:03 +03:00
numa_memblks.c mm: numa_memblks: use numa_add_reserved_memblk() in numa_cleanup_meminfo() 2026-07-03 11:16:27 +03:00
numa.c
oom_kill.c mm/oom_kill.c: simpilfy rcu call with guard(rcu) 2026-04-05 13:53:17 -07:00
page_alloc.c mm/page_alloc: only update lowmem_reserve_ratio on sysctl write 2026-08-24 18:43:01 -07:00
page_alloc.h mm: replace __GFP_NO_CODETAG with ALLOC_NO_CODETAG 2026-07-30 19:40:44 -07:00
page_counter.c
page_ext.c mm/page_ext: remove pgdat_page_ext_init() 2026-08-24 18:43:03 -07:00
page_frag_cache.c mm: replace __GFP_NO_CODETAG with ALLOC_NO_CODETAG 2026-07-30 19:40:44 -07:00
page_idle.c mm/page_idle.c: remove redundant mmu notifier in aging code 2026-04-05 13:53:02 -07:00
page_io.c mm/swap: move swap_ops into file systems for file system-based swap 2026-08-24 18:43:20 -07:00
page_isolation.c mm: split out internal page_alloc.h 2026-07-30 19:40:41 -07:00
page_owner.c mm: split out internal page_alloc.h 2026-07-30 19:40:41 -07:00
page_poison.c
page_reporting.c mm/page_reporting: add page_reporting_delay_ms module parameter 2026-08-24 18:42:58 -07:00
page_reporting.h
page_table_check.c Merge branch 'mm-hotfixes-stable' into mm-stable to pick up 2026-08-24 18:40:27 -07:00
page_vma_mapped.c mm/rmap: use anon pgoff to track MAP_PRIVATE file-backed anon folios 2026-08-24 18:42:53 -07:00
page-writeback.c mm.git review status for linus..mm-stable 2026-08-27 09:17:06 -07:00
pagewalk.c Merge branch 'mm-hotfixes-stable' into mm-stable to pick up 2026-08-24 18:40:27 -07:00
percpu-internal.h mm/percpu-internal.h: optimise pcpu_chunk struct to save memory 2026-06-02 15:22:13 -07:00
percpu-km.c mm/percpu-km: clear page->private before free them 2026-08-04 19:18:32 -07:00
percpu-stats.c
percpu-vm.c mm: split out vmalloc declarations from internal.h 2026-08-04 19:18:46 -07:00
percpu.c mm/percpu: avoid IO/FS reclaim in backing allocations 2026-07-28 21:11:47 -07:00
pgalloc-track.h mm: add some missing includes to mm-local headers 2026-08-24 18:43:03 -07:00
pgtable-generic.c mm: change to return bool for pmdp_clear_flush_young() 2026-04-05 13:53:35 -07:00
process_vm_access.c
ptdump.c mm/ptdump: always stabilise against page table freeing using init_mm 2026-08-04 20:02:00 -07:00
readahead.c block: split out a new blk_plug.h header 2026-08-04 06:57:05 -06:00
rmap.c mm/rmap: synchronize lock and unlock target in anon_vma_clone 2026-08-24 18:43:25 -07:00
rodata_test.c
secretmem.c mm/secretmem: don't allow highmem folios 2026-08-06 18:57:09 -07:00
shmem_quota.c treewide: Replace kmalloc with kmalloc_obj for non-scalar types 2026-02-21 01:02:28 -08:00
shmem.c mm.git review status for linus..mm-stable 2026-08-27 09:17:06 -07:00
show_mem.c mm/show_mem: fix format string inconsistencies and type mismatches 2026-08-24 18:43:06 -07:00
shrinker_debug.c mm: shrinker: fix NULL pointer dereference in debugfs 2026-07-01 19:02:52 -07:00
shrinker.c mm: shrinker: fix shrinker_info teardown race with expansion 2026-07-01 19:02:52 -07:00
shuffle.c mm: split out internal page_alloc.h 2026-07-30 19:40:41 -07:00
shuffle.h mm: add some missing includes to mm-local headers 2026-08-24 18:43:03 -07:00
slab_common.c slab changes for 7.3 2026-08-24 10:58:57 -07:00
slab.h slab changes for 7.3 2026-08-24 10:58:57 -07:00
slub.c slab changes for 7.3 2026-08-24 10:58:57 -07:00
sparse-vmemmap.c mm: split out sparse declarations from internal.h 2026-08-04 19:18:46 -07:00
sparse.c mm/sparse: keep mem_section_usage_size() internal 2026-08-24 18:43:06 -07:00
sparse.h mm/sparse: keep mem_section_usage_size() internal 2026-08-24 18:43:06 -07:00
swap_state.c mm.git review status for linus..mm-stable 2026-08-27 09:17:06 -07:00
swap_table.h mm, swap: merge zeromap into swap table 2026-06-02 15:22:23 -07:00
swap.h mm/swap: add a new swap_ops.h header to allow for pluggable swap ops 2026-08-24 18:43:20 -07:00
swapfile.c mm, swap: ratelimit bad swap entry reports 2026-08-24 18:43:27 -07:00
truncate.c mm/truncate: use folio_split() in truncate_inode_partial_folio() 2026-06-21 11:37:16 -07:00
usercopy.c
userfaultfd.c mm/rmap: use anon pgoff to track MAP_PRIVATE file-backed anon folios 2026-08-24 18:42:53 -07:00
util.c mm/vma: update do_mmap() to use vma_flags_t 2026-08-06 18:57:01 -07:00
vma_exec.c mm: propagate VMA anonymous page offset on map, remap, split + merge 2026-08-24 18:42:52 -07:00
vma_init.c mm/vma: introduce VMA anon page offset field and add helpers 2026-08-24 18:42:49 -07:00
vma_internal.h mm/vma: correct incorrect vma.h inclusion 2026-08-04 19:19:04 -07:00
vma.c mm/rmap: use anon pgoff to track MAP_PRIVATE file-backed anon folios 2026-08-24 18:42:53 -07:00
vma.h mm: propagate VMA anonymous page offset on map, remap, split + merge 2026-08-24 18:42:52 -07:00
vmalloc.c mm/vmalloc: do not warn on -ENOMEM from va_alloc() 2026-08-24 18:43:02 -07:00
vmalloc.h mm: add some missing includes to mm-local headers 2026-08-24 18:43:03 -07:00
vmpressure.c mm/vmpressure: move v1 userspace eventfd code into memcontrol-v1.c 2026-07-30 19:40:28 -07:00
vmscan.c mm.git review status for linus..mm-stable 2026-08-27 09:17:06 -07:00
vmstat.c mm/vmstat: add NRSWP{IN,OUT} counters 2026-08-24 18:43:15 -07:00
workingset.c mm/vmscan: reduce lru_lock contention via vmstat-derived scan-balance cost 2026-08-24 18:42:56 -07:00
zpdesc.h
zsmalloc.c zsmalloc: account for handle size in class lookup 2026-08-24 18:43:19 -07:00
zswap.c mm/swap: add a new swap_ops.h header to allow for pluggable swap ops 2026-08-24 18:43:20 -07:00