[PATCH] dma-buf/udmabuf: don't warn on oversized allocation requests
From: Priyanka Mani
Date: Fri Sep 18 2026 - 04:29:39 EST
udmabuf_create() derives the number of pages to allocate directly from
the size supplied by userspace, bounded only by the size_limit_mb module
parameter. Since commit 44e9eb5a7621 ("dma-buf/udmabuf: Disable the size
limit by default") that parameter defaults to INT_MAX, which puts the
page count limit at roughly 5.5e11 pages, i.e. no limit in practice.
init_udmabuf() then asks kvmalloc_objs() for pgcnt * sizeof(struct page *)
bytes. __kvmalloc_node_noprof() refuses any request larger than INT_MAX
and splats WARN_ON_ONCE(!(flags & __GFP_NOWARN)) on its way out, while
kvmalloc_objs() defaults to a plain GFP_KERNEL.
A single UDMABUF_CREATE against /dev/udmabuf with a sufficiently large
size is therefore all it takes to trigger:
------------[ cut here ]------------
WARNING: mm/slub.c:7022 at __kvmalloc_node_noprof+0x412/0x5a0
Call Trace:
udmabuf_create+0x11f/0x540
udmabuf_ioctl+0xf1/0x190
__x64_sys_ioctl+0x91/0xe0
do_syscall_64+0xdd/0x4a0
The size is entirely userspace-controlled and allocation failure is
already handled by returning -ENOMEM to the caller, so this is not a
condition the kernel needs to complain about. Pass __GFP_NOWARN and let
the existing error path do its job.
Note that capping the limit instead would change the error reported to
userspace from -ENOMEM to -EINVAL and would reintroduce a fixed ceiling
that the above commit deliberately removed, so __GFP_NOWARN seems the
more faithful fix.
Reported-by: syzbot+bfeed181d1ce9ec87a8f@xxxxxxxxxxxxxxxxxxxxxxxxx
Closes: https://syzkaller.appspot.com/bug?extid=bfeed181d1ce9ec87a8f
Fixes: 44e9eb5a7621 ("dma-buf/udmabuf: Disable the size limit by default")
Signed-off-by: Priyanka Mani <priyankamani2100@xxxxxxxxx>
---
drivers/dma-buf/udmabuf.c | 6 ++++--
1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/drivers/dma-buf/udmabuf.c b/drivers/dma-buf/udmabuf.c
index df6dd0046242..127369e502a3 100644
--- a/drivers/dma-buf/udmabuf.c
+++ b/drivers/dma-buf/udmabuf.c
@@ -190,11 +190,13 @@ static void unpin_all_folios(struct udmabuf *ubuf)
static __always_inline int init_udmabuf(struct udmabuf *ubuf, pgoff_t pgcnt)
{
- ubuf->pages = kvmalloc_objs(*ubuf->pages, pgcnt);
+ ubuf->pages = kvmalloc_objs(*ubuf->pages, pgcnt,
+ GFP_KERNEL | __GFP_NOWARN);
if (!ubuf->pages)
return -ENOMEM;
- ubuf->pinned_folios = kvmalloc_objs(*ubuf->pinned_folios, pgcnt);
+ ubuf->pinned_folios = kvmalloc_objs(*ubuf->pinned_folios, pgcnt,
+ GFP_KERNEL | __GFP_NOWARN);
if (!ubuf->pinned_folios)
return -ENOMEM;
--
2.43.0