]> git.ipfire.org Git - thirdparty/linux.git/commit
slab: Introduce kmalloc_flex() and family
authorKees Cook <kees@kernel.org>
Wed, 3 Dec 2025 23:30:34 +0000 (15:30 -0800)
committerKees Cook <kees@kernel.org>
Wed, 14 Jan 2026 22:43:01 +0000 (14:43 -0800)
commite4c8b46b924eb8de66c6f0accc9cdd0c2e8fa23b
tree8670c3d9c332b8e93ededb7f9ae93320b1b7edc6
parent81cee9166a9073b4da28e970e75d7f89c98ed966
slab: Introduce kmalloc_flex() and family

As done for kmalloc_obj*(), introduce a type-aware allocator for flexible
arrays, which may also have "counted_by" annotations:

ptr = kmalloc(struct_size(ptr, flex_member, count), gfp);

becomes:

ptr = kmalloc_flex(*ptr, flex_member, count, gfp);

The internal use of __flex_counter() allows for automatically setting
the counter member of a struct's flexible array member when it has
been annotated with __counted_by(), avoiding any missed early size
initializations while __counted_by() annotations are added to the
kernel. Additionally, this also checks for "too large" allocations based
on the type size of the counter variable. For example:

if (count > type_max(ptr->flex_counter))
fail...;
size = struct_size(ptr, flex_member, count);
ptr = kmalloc(size, gfp);
if (!ptr)
fail...;
ptr->flex_counter = count;

becomes (n.b. unchanged from earlier example):

ptr = kmalloc_flex(*ptr, flex_member, count, gfp);
if (!ptr)
fail...;
ptr->flex_counter = count;

Note that manual initialization of the flexible array counter is still
required (at some point) after allocation as not all compiler versions
support the __counted_by annotation yet. But doing it internally makes
sure they cannot be missed when __counted_by _is_ available, meaning
that the bounds checker will not trip due to the lack of "early enough"
initializations that used to work before enabling the stricter bounds
checking. For example:

ptr = kmalloc_flex(*ptr, flex_member, count, gfp);
fill(ptr->flex, count);
ptr->flex_count = count;

This works correctly before adding a __counted_by annotation (since
nothing is checking ptr->flex accesses against ptr->flex_count). After
adding the annotation, the bounds sanitizer would trip during fill()
because ptr->flex_count wasn't set yet. But with kmalloc_flex() setting
ptr->flex_count internally at allocation time, the existing code works
without needing to move the ptr->flex_count assignment before the call
to fill(). (This has been a stumbling block for __counted_by adoption.)

Link: https://patch.msgid.link/20251203233036.3212363-4-kees@kernel.org
Acked-by: Vlastimil Babka <vbabka@suse.cz>
Signed-off-by: Kees Cook <kees@kernel.org>
Documentation/process/deprecated.rst
include/linux/slab.h