diff options
| author | Hongfu Li <lihongfu@kylinos.cn> | 2026-05-12 15:14:24 +0800 |
|---|---|---|
| committer | Tejun Heo <tj@kernel.org> | 2026-05-12 07:31:39 -1000 |
| commit | 2a7d34eba5f5a9b889c0f24a28c3b603ba1e7b2b (patch) | |
| tree | 07081fe2af5a628e50f0675841f666b2a9fc6835 /tools/testing | |
| parent | be2689c9ed47bde6f15a24c9845f6fc1ec52502f (diff) | |
| download | linux-next-2a7d34eba5f5a9b889c0f24a28c3b603ba1e7b2b.tar.gz linux-next-2a7d34eba5f5a9b889c0f24a28c3b603ba1e7b2b.zip | |
selftests/cgroup: check malloc return value in alloc_anon functions
The alloc_anon() function calls malloc() without checking for a NULL
return. If memory allocation fails, a NULL pointer dereference will
occur when accessing the buffer.
Add proper error handling to return -1 when malloc() fails in all
four alloc_anon variants:
- alloc_anon()
- alloc_anon_50M_check()
- alloc_anon_noexit()
- alloc_anon_50M_check_swap()
Signed-off-by: Hongfu Li <lihongfu@kylinos.cn>
Reviewed-by: Vishal Moola <vishal.moola@gmail.com>
Reviewed-by: Muchun Song <muchun.song@linux.dev>
Signed-off-by: Tejun Heo <tj@kernel.org>
Diffstat (limited to 'tools/testing')
| -rw-r--r-- | tools/testing/selftests/cgroup/test_memcontrol.c | 53 |
1 files changed, 27 insertions, 26 deletions
diff --git a/tools/testing/selftests/cgroup/test_memcontrol.c b/tools/testing/selftests/cgroup/test_memcontrol.c index b43da9bc20c4..21aedb35cc12 100644 --- a/tools/testing/selftests/cgroup/test_memcontrol.c +++ b/tools/testing/selftests/cgroup/test_memcontrol.c @@ -55,15 +55,31 @@ cleanup: return -1; } -int alloc_anon(const char *cgroup, void *arg) +static char *alloc_and_populate_anon(size_t size) { - size_t size = (unsigned long)arg; char *buf, *ptr; buf = malloc(size); + if (buf == NULL) { + fprintf(stderr, "malloc() failed\n"); + return NULL; + } + for (ptr = buf; ptr < buf + size; ptr += PAGE_SIZE) *ptr = 0; + return buf; +} + +int alloc_anon(const char *cgroup, void *arg) +{ + size_t size = (unsigned long)arg; + char *buf; + + buf = alloc_and_populate_anon(size); + if (!buf) + return -1; + free(buf); return 0; } @@ -174,18 +190,13 @@ cleanup_free: static int alloc_anon_50M_check(const char *cgroup, void *arg) { size_t size = MB(50); - char *buf, *ptr; + char *buf; long anon, current; int ret = -1; - buf = malloc(size); - if (buf == NULL) { - fprintf(stderr, "malloc() failed\n"); + buf = alloc_and_populate_anon(size); + if (!buf) return -1; - } - - for (ptr = buf; ptr < buf + size; ptr += PAGE_SIZE) - *ptr = 0; current = cg_read_long(cgroup, "memory.current"); if (current < size) @@ -406,16 +417,11 @@ static int alloc_anon_noexit(const char *cgroup, void *arg) { int ppid = getppid(); size_t size = (unsigned long)arg; - char *buf, *ptr; + char *buf; - buf = malloc(size); - if (buf == NULL) { - fprintf(stderr, "malloc() failed\n"); + buf = alloc_and_populate_anon(size); + if (!buf) return -1; - } - - for (ptr = buf; ptr < buf + size; ptr += PAGE_SIZE) - *ptr = 0; while (getppid() == ppid) sleep(1); @@ -990,18 +996,13 @@ static int alloc_anon_50M_check_swap(const char *cgroup, void *arg) { long mem_max = (long)arg; size_t size = MB(50); - char *buf, *ptr; + char *buf; long mem_current, swap_current; int ret = -1; - buf = malloc(size); - if (buf == NULL) { - fprintf(stderr, "malloc() failed\n"); + buf = alloc_and_populate_anon(size); + if (!buf) return -1; - } - - for (ptr = buf; ptr < buf + size; ptr += PAGE_SIZE) - *ptr = 0; mem_current = cg_read_long(cgroup, "memory.current"); if (!mem_current || !values_close(mem_current, mem_max, 3)) |
