hulk inclusion category: bugfix bugzilla: https://gitee.com/openeuler/kernel/issues/I90E0C CVE: NA
--------------------------------
Patchset[1] supports to remove the sentinel element in the ctl_table when registering it to sysctl. However, the patchset fails to handle when the array is empty, leading to out-of-bound access in insert_header.
When CONFIG_MEMCG_OOM_PRIORITY and CONFIG_MEMCG_SWAP_QOS are disabled, mem_cgroup_sysctls is a empty array, mem_cgroup_sysctls_init() calls register_sysctl_init() to register it. This leads to out-of-bound access. The KASAN report is as follows:
================================================================== BUG: KASAN: global-out-of-bounds in insert_header+0x4b/0x2b0 Read of size 4 at addr ffffffff99c03a58 by task swapper/0/1
Call Trace: <TASK> dump_stack_lvl+0x37/0x50 print_address_description.constprop.0+0x6b/0x3d0 ? insert_header+0x4b/0x2b0 print_report+0xb5/0x270 ? kasan_addr_to_slab+0xd/0xa0 kasan_report+0xb0/0xe0 ? insert_header+0x4b/0x2b0 insert_header+0x4b/0x2b0 __register_sysctl_table+0x1d3/0x220 __register_sysctl_init+0x24/0x50 mem_cgroup_init+0x1cd/0x1e0 ? __pfx_mem_cgroup_init+0x10/0x10 do_one_initcall+0x8e/0x320 ? __pfx_do_one_initcall+0x10/0x10 ? __pfx_parse_args+0x10/0x10 ? __kmem_cache_alloc_node+0x1e0/0x480 ? kasan_set_track+0x25/0x30 ? __kasan_kmalloc+0x7f/0x90 do_initcalls+0xe0/0x1b0 kernel_init_freeable+0x242/0x320 ? __pfx_kernel_init+0x10/0x10 kernel_init+0x1f/0x1e0 ? calculate_sigpending+0x63/0x70 ret_from_fork+0x34/0x60 ? __pfx_kernel_init+0x10/0x10 ret_from_fork_asm+0x1b/0x30 </TASK>
The buggy address belongs to the variable: mem_cgroup_sysctls+0x18/0x20
The buggy address belongs to the physical page:
Memory state around the buggy address: ffffffff99c03900: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ffffffff99c03980: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
ffffffff99c03a00: f9 f9 f9 f9 f9 f9 f9 f9 f9 f9 f9 f9 00 00 f9 f9
^ ffffffff99c03a80: f9 f9 f9 f9 04 f9 f9 f9 f9 f9 f9 f9 00 f9 f9 f9 ffffffff99c03b00: f9 f9 f9 f9 04 f9 f9 f9 f9 f9 f9 f9 04 f9 f9 f9 ==================================================================
To fix it, check if mem_cgroup_sysctls is a empty array before calling register_sysctl_init().
[1] https://lore.kernel.org/lkml/20230809105006.1198165-1-j.granados@samsung.com...
Signed-off-by: Jinjiang Tu tujinjiang@huawei.com --- mm/memcontrol.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/mm/memcontrol.c b/mm/memcontrol.c index 346be8292294..df2fc279a666 100644 --- a/mm/memcontrol.c +++ b/mm/memcontrol.c @@ -8531,7 +8531,8 @@ static __init int mem_cgroup_sysctls_init(void) if (mem_cgroup_disabled()) return 0;
- register_sysctl_init("vm", mem_cgroup_sysctls); + if (ARRAY_SIZE(mem_cgroup_sysctls)) + register_sysctl_init("vm", mem_cgroup_sysctls); return 0; } #else