CVE-2026-89966 in Linux
Summary
by MITRE • 09/16/2026
In the Linux kernel, the following vulnerability has been resolved:
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
If you want to get best quality of vulnerability data, you may have to visit VulDB.
Analysis
by VulDB Data Team • 09/16/2026
The Linux kernel contains a critical null pointer dereference vulnerability within the huge page memory management subsystem, specifically in the function hugetlb_cma_alloc_frozen_folio located in mm/hugetlb_cma.c. This flaw arises from an incomplete validation of nodemask parameters passed through the allocation chain for gigantic hugepages. The issue is triggered when alloc_buddy_hugetlb_folio_with_mpol attempts to allocate memory using a policy that falls back to allocating from all nodes, thereby passing a NULL nodemask down to alloc_fresh_hugetlb_folio and subsequently to hugetlb_cma_alloc_frozen_folio via the intermediate function alloc_gigantic_frozen_folio. The root cause lies in the fact that while the code attempts to verify if a specific node identifier is included in the caller's nodemask using node_isset, it fails to check whether the nodemask pointer itself is NULL before dereferencing it. This oversight leads directly to a kernel panic when the system encounters this execution path with a null reference.
From an operational perspective, this vulnerability allows for a local denial of service attack against the entire operating system. An unprivileged user can exploit this flaw by requesting a gigantic hugepage allocation using the MPOL_PREFERRED_MANY memory policy on systems where Contiguous Memory Allocator is configured only on a subset of NUMA nodes. By mapping a large anonymous region with MAP_HUGETLB and then binding it to a specific node that lacks CMA support, followed by triggering a page fault through memory access, the user forces the kernel into the vulnerable code path. The resulting null pointer dereference causes an immediate system crash, effectively rendering the machine unavailable until rebooted. This represents a significant stability risk in multi-node environments where hugepage allocations are common or when applications utilize advanced memory placement policies without proper privilege restrictions on such operations.
The technical fix involves modifying hugetlb_cma_alloc_frozen_folio to explicitly check if the nodemask is NULL before attempting any dereference operations. If a null mask is detected, the function defaults to using cpuset_current_mems_allowed, which represents the current task's allowed memory nodes. Furthermore, the allocation attempts are enclosed within a cpuset seqcount retry loop. This ensures that if the cpuset configuration changes concurrently during the allocation process, the system retries with an updated nodemask rather than proceeding with stale or invalid data. This approach not only prevents the null pointer dereference but also guarantees that memory allocations strictly honor task-specific cpuset constraints and NUMA policies, thereby maintaining both security integrity and performance consistency across complex hardware topologies.
This vulnerability aligns with CWE-476, which describes a NULL Pointer Dereference, as the core failure is the lack of validation for a pointer before its use in critical kernel functions. In terms of attack classification under MITRE ATT&CK, this falls under T1053 Scheduled Task/Job or more accurately T1059 Command and Scripting Interpreter if viewed through the lens of local exploitation leading to system disruption, but primarily it is categorized as a Denial of Service (DoS) vector due to its ability to crash the host. The remediation strategy emphasizes defensive programming practices by validating input parameters at entry points into sensitive subsystems like memory management. System administrators should ensure that kernel updates incorporating this fix are applied promptly, particularly on servers utilizing NUMA architectures with large page sizes and custom CMA configurations. Additionally, userspace applications relying on hugepages should be audited to ensure they handle allocation failures gracefully rather than assuming successful mapping under all policy constraints.