public inbox for stable@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH bpf] bpf: do not use kmalloc_nolock when !HAVE_CMPXCHG_DOUBLE
@ 2026-03-14 10:36 Levi Zim via B4 Relay
  2026-03-14 11:09 ` bot+bpf-ci
  2026-03-14 17:05 ` kernel test robot
  0 siblings, 2 replies; 4+ messages in thread
From: Levi Zim via B4 Relay @ 2026-03-14 10:36 UTC (permalink / raw)
  To: Alexei Starovoitov, Daniel Borkmann, Andrii Nakryiko,
	Martin KaFai Lau, Eduard Zingerman, Song Liu, Yonghong Song,
	John Fastabend, KP Singh, Stanislav Fomichev, Hao Luo, Jiri Olsa,
	Sebastian Andrzej Siewior, Clark Williams, Steven Rostedt,
	Paul Walmsley, Palmer Dabbelt, Albert Ou, Alexandre Ghiti
  Cc: Amery Hung, linux-riscv, stable, bpf, linux-kernel,
	linux-rt-devel, Levi Zim

From: Levi Zim <rsworktech@outlook.com>

kmalloc_nolock always fails for architectures that lack cmpxchg16b.
For example, this causes bpf_task_storage_get with flag
BPF_LOCAL_STORAGE_GET_F_CREATE to fails on riscv64 6.19 kernel.

Fix it by enabling use_kmalloc_nolock only when HAVE_CMPXCHG_DOUBLE

Fixes: f484f4a3e058 ("bpf: Replace bpf memory allocator with kmalloc_nolock() in local storage")
Cc: stable@vger.kernel.org
Signed-off-by: Levi Zim <rsworktech@outlook.com>
---
I find that bpf_task_storage_get with flag BPF_LOCAL_STORAGE_GET_F_CREATE
always fails for me on 6.19 kernel on riscv64 and bisected it.

In f484f4a3e058 ("bpf: Replace bpf memory allocator with kmalloc_nolock()
in local storage"), bpf memory allocator is replaced with kmalloc_nolock.
This approach is problematic for architectures that lack CMPXCHG_DOUBLE
because kmalloc_nolock always fails in this case:

In function kmalloc_nolock (kmalloc_nolock_noprof): 

	if (!(s->flags & __CMPXCHG_DOUBLE) && !kmem_cache_debug(s))
		/*
		 * kmalloc_nolock() is not supported on architectures that
		 * don't implement cmpxchg16b, but debug caches don't use
		 * per-cpu slab and per-cpu partial slabs. They rely on
		 * kmem_cache_node->list_lock, so kmalloc_nolock() can
		 * attempt to allocate from debug caches by
		 * spin_trylock_irqsave(&n->list_lock, ...)
		 */
		return NULL;

Fix it by enabling use_kmalloc_nolock only when HAVE_CMPXCHG_DOUBLE.

Note for stable: this only needs to be picked into v6.19 if the patch
makes it into 7.0.
---
 include/linux/bpf_local_storage.h | 2 ++
 kernel/bpf/bpf_cgrp_storage.c     | 2 +-
 kernel/bpf/bpf_local_storage.c    | 3 ++-
 kernel/bpf/bpf_task_storage.c     | 2 +-
 4 files changed, 6 insertions(+), 3 deletions(-)

diff --git a/include/linux/bpf_local_storage.h b/include/linux/bpf_local_storage.h
index 8157e8da61d40..a7ae5dde15bcb 100644
--- a/include/linux/bpf_local_storage.h
+++ b/include/linux/bpf_local_storage.h
@@ -19,6 +19,8 @@
 
 #define BPF_LOCAL_STORAGE_CACHE_SIZE	16
 
+static const bool KMALLOC_NOLOCK_SUPPORTED = IS_ENABLED(CONFIG_HAVE_CMPXCHG_DOUBLE);
+
 struct bpf_local_storage_map_bucket {
 	struct hlist_head list;
 	rqspinlock_t lock;
diff --git a/kernel/bpf/bpf_cgrp_storage.c b/kernel/bpf/bpf_cgrp_storage.c
index c2a2ead1f466d..09c557e426968 100644
--- a/kernel/bpf/bpf_cgrp_storage.c
+++ b/kernel/bpf/bpf_cgrp_storage.c
@@ -114,7 +114,7 @@ static int notsupp_get_next_key(struct bpf_map *map, void *key, void *next_key)
 
 static struct bpf_map *cgroup_storage_map_alloc(union bpf_attr *attr)
 {
-	return bpf_local_storage_map_alloc(attr, &cgroup_cache, true);
+	return bpf_local_storage_map_alloc(attr, &cgroup_cache, KMALLOC_NOLOCK_SUPPORTED);
 }
 
 static void cgroup_storage_map_free(struct bpf_map *map)
diff --git a/kernel/bpf/bpf_local_storage.c b/kernel/bpf/bpf_local_storage.c
index 9c96a4477f81a..8e4b0fe6d12af 100644
--- a/kernel/bpf/bpf_local_storage.c
+++ b/kernel/bpf/bpf_local_storage.c
@@ -894,7 +894,8 @@ bpf_local_storage_map_alloc(union bpf_attr *attr,
 	 * preemptible context. Thus, enforce all storages to use
 	 * kmalloc_nolock() when CONFIG_PREEMPT_RT is enabled.
 	 */
-	smap->use_kmalloc_nolock = IS_ENABLED(CONFIG_PREEMPT_RT) ? true : use_kmalloc_nolock;
+	smap->use_kmalloc_nolock = IS_ENABLED(CONFIG_PREEMPT_RT) &&
+		KMALLOC_NOLOCK_SUPPORTED ? true : use_kmalloc_nolock;
 
 	smap->cache_idx = bpf_local_storage_cache_idx_get(cache);
 	return &smap->map;
diff --git a/kernel/bpf/bpf_task_storage.c b/kernel/bpf/bpf_task_storage.c
index 605506792b5b4..9f74fd1ef7f46 100644
--- a/kernel/bpf/bpf_task_storage.c
+++ b/kernel/bpf/bpf_task_storage.c
@@ -212,7 +212,7 @@ static int notsupp_get_next_key(struct bpf_map *map, void *key, void *next_key)
 
 static struct bpf_map *task_storage_map_alloc(union bpf_attr *attr)
 {
-	return bpf_local_storage_map_alloc(attr, &task_cache, true);
+	return bpf_local_storage_map_alloc(attr, &task_cache, KMALLOC_NOLOCK_SUPPORTED);
 }
 
 static void task_storage_map_free(struct bpf_map *map)

---
base-commit: e06e6b8001233241eb5b2e2791162f0585f50f4b
change-id: 20260314-bpf-kmalloc-nolock-60da80e613de

Best regards,
-- 
Levi Zim <rsworktech@outlook.com>



^ permalink raw reply related	[flat|nested] 4+ messages in thread

* Re: [PATCH bpf] bpf: do not use kmalloc_nolock when !HAVE_CMPXCHG_DOUBLE
  2026-03-14 10:36 [PATCH bpf] bpf: do not use kmalloc_nolock when !HAVE_CMPXCHG_DOUBLE Levi Zim via B4 Relay
@ 2026-03-14 11:09 ` bot+bpf-ci
  2026-03-14 15:17   ` Levi Zim
  2026-03-14 17:05 ` kernel test robot
  1 sibling, 1 reply; 4+ messages in thread
From: bot+bpf-ci @ 2026-03-14 11:09 UTC (permalink / raw)
  To: rsworktech, ast, daniel, andrii, martin.lau, eddyz87, song,
	yonghong.song, john.fastabend, kpsingh, sdf, haoluo, jolsa,
	bigeasy, clrkwllms, rostedt, pjw, palmer, aou, alex
  Cc: ameryhung, linux-riscv, stable, bpf, linux-kernel, linux-rt-devel,
	rsworktech, ast, andrii, daniel, martin.lau, eddyz87,
	yonghong.song, clm, ihor.solodrai

[-- Attachment #1: Type: text/plain, Size: 1254 bytes --]

> diff --git a/kernel/bpf/bpf_local_storage.c b/kernel/bpf/bpf_local_storage.c
> index 9c96a4477f81..8e4b0fe6d12a 100644
> --- a/kernel/bpf/bpf_local_storage.c
> +++ b/kernel/bpf/bpf_local_storage.c
> @@ -894,7 +894,8 @@ bpf_local_storage_map_alloc(union bpf_attr *attr,
>  	 * preemptible context. Thus, enforce all storages to use
>  	 * kmalloc_nolock() when CONFIG_PREEMPT_RT is enabled.
>  	 */
> -	smap->use_kmalloc_nolock = IS_ENABLED(CONFIG_PREEMPT_RT) ? true : use_kmalloc_nolock;
> +	smap->use_kmalloc_nolock = IS_ENABLED(CONFIG_PREEMPT_RT) &&
> +		KMALLOC_NOLOCK_SUPPORTED ? true : use_kmalloc_nolock;

Should the comment above be updated to reflect the new behavior?
It currently says "enforce all storages to use kmalloc_nolock()
when CONFIG_PREEMPT_RT is enabled", but the code now only enforces
kmalloc_nolock when both CONFIG_PREEMPT_RT and
CONFIG_HAVE_CMPXCHG_DOUBLE are enabled. On PREEMPT_RT without
HAVE_CMPXCHG_DOUBLE, the override is silently skipped and the
caller's value is used instead.


---
AI reviewed your patch. Please fix the bug or email reply why it's not a bug.
See: https://github.com/kernel-patches/vmtest/blob/master/ci/claude/README.md

CI run summary: https://github.com/kernel-patches/bpf/actions/runs/23086356774

^ permalink raw reply	[flat|nested] 4+ messages in thread

* Re: [PATCH bpf] bpf: do not use kmalloc_nolock when !HAVE_CMPXCHG_DOUBLE
  2026-03-14 11:09 ` bot+bpf-ci
@ 2026-03-14 15:17   ` Levi Zim
  0 siblings, 0 replies; 4+ messages in thread
From: Levi Zim @ 2026-03-14 15:17 UTC (permalink / raw)
  To: bot+bpf-ci, ast, daniel, andrii, martin.lau, eddyz87, song,
	yonghong.song, john.fastabend, kpsingh, sdf, haoluo, jolsa,
	bigeasy, clrkwllms, rostedt, pjw, palmer, aou, alex
  Cc: ameryhung, linux-riscv, stable, bpf, linux-kernel, linux-rt-devel,
	martin.lau, clm, ihor.solodrai

Hi,

On 3/14/26 7:09 PM, bot+bpf-ci@kernel.org wrote:
>> diff --git a/kernel/bpf/bpf_local_storage.c b/kernel/bpf/bpf_local_storage.c
>> index 9c96a4477f81..8e4b0fe6d12a 100644
>> --- a/kernel/bpf/bpf_local_storage.c
>> +++ b/kernel/bpf/bpf_local_storage.c
>> @@ -894,7 +894,8 @@ bpf_local_storage_map_alloc(union bpf_attr *attr,
>>  	 * preemptible context. Thus, enforce all storages to use
>>  	 * kmalloc_nolock() when CONFIG_PREEMPT_RT is enabled.
>>  	 */
>> -	smap->use_kmalloc_nolock = IS_ENABLED(CONFIG_PREEMPT_RT) ? true : use_kmalloc_nolock;
>> +	smap->use_kmalloc_nolock = IS_ENABLED(CONFIG_PREEMPT_RT) &&
>> +		KMALLOC_NOLOCK_SUPPORTED ? true : use_kmalloc_nolock;
> 
> Should the comment above be updated to reflect the new behavior?
> It currently says "enforce all storages to use kmalloc_nolock()
> when CONFIG_PREEMPT_RT is enabled", but the code now only enforces
> kmalloc_nolock when both CONFIG_PREEMPT_RT and
> CONFIG_HAVE_CMPXCHG_DOUBLE are enabled. On PREEMPT_RT without
> HAVE_CMPXCHG_DOUBLE, the override is silently skipped and the
> caller's value is used instead.

I didn't give it too much thought initially. So the kmalloc_nolock() usage in PREEMPT_RT
context is necessary for correctness. I will remove "&& KMALLOC_NOLOCK_SUPPORTED" in v2
and add a comment to explain the current limitation when PREEMPT_RT is combined with
an architecture that doesn't HAVE_CMPXCHG_DOUBLE.

Best regards,
Levi

> 
> ---
> AI reviewed your patch. Please fix the bug or email reply why it's not a bug.
> See: https://github.com/kernel-patches/vmtest/blob/master/ci/claude/README.md
> 
> CI run summary: https://github.com/kernel-patches/bpf/actions/runs/23086356774


^ permalink raw reply	[flat|nested] 4+ messages in thread

* Re: [PATCH bpf] bpf: do not use kmalloc_nolock when !HAVE_CMPXCHG_DOUBLE
  2026-03-14 10:36 [PATCH bpf] bpf: do not use kmalloc_nolock when !HAVE_CMPXCHG_DOUBLE Levi Zim via B4 Relay
  2026-03-14 11:09 ` bot+bpf-ci
@ 2026-03-14 17:05 ` kernel test robot
  1 sibling, 0 replies; 4+ messages in thread
From: kernel test robot @ 2026-03-14 17:05 UTC (permalink / raw)
  To: Levi Zim via B4 Relay, Alexei Starovoitov, Daniel Borkmann,
	Andrii Nakryiko, Martin KaFai Lau, Eduard Zingerman, Song Liu,
	Yonghong Song, John Fastabend, KP Singh, Stanislav Fomichev,
	Hao Luo, Jiri Olsa, Sebastian Andrzej Siewior, Clark Williams,
	Steven Rostedt, Paul Walmsley, Palmer Dabbelt, Albert Ou,
	Alexandre Ghiti
  Cc: oe-kbuild-all, Amery Hung, linux-riscv, stable, bpf, linux-kernel,
	linux-rt-devel, Levi Zim

Hi Levi,

kernel test robot noticed the following build warnings:

[auto build test WARNING on e06e6b8001233241eb5b2e2791162f0585f50f4b]

url:    https://github.com/intel-lab-lkp/linux/commits/Levi-Zim-via-B4-Relay/bpf-do-not-use-kmalloc_nolock-when-HAVE_CMPXCHG_DOUBLE/20260314-195705
base:   e06e6b8001233241eb5b2e2791162f0585f50f4b
patch link:    https://lore.kernel.org/r/20260314-bpf-kmalloc-nolock-v1-1-24abf3f75a9f%40outlook.com
patch subject: [PATCH bpf] bpf: do not use kmalloc_nolock when !HAVE_CMPXCHG_DOUBLE
config: x86_64-rhel-9.4 (https://download.01.org/0day-ci/archive/20260314/202603141857.sLJ0vJoa-lkp@intel.com/config)
compiler: gcc-14 (Debian 14.2.0-19) 14.2.0
reproduce (this is a W=1 build): (https://download.01.org/0day-ci/archive/20260314/202603141857.sLJ0vJoa-lkp@intel.com/reproduce)

If you fix the issue in a separate patch/commit (i.e. not just a new version of
the same patch/commit), kindly add following tags
| Reported-by: kernel test robot <lkp@intel.com>
| Closes: https://lore.kernel.org/oe-kbuild-all/202603141857.sLJ0vJoa-lkp@intel.com/

All warnings (new ones prefixed by >>):

   In file included from include/net/bpf_sk_storage.h:15,
                    from net/core/sock.c:141:
>> include/linux/bpf_local_storage.h:22:19: warning: 'KMALLOC_NOLOCK_SUPPORTED' defined but not used [-Wunused-const-variable=]
      22 | static const bool KMALLOC_NOLOCK_SUPPORTED = IS_ENABLED(CONFIG_HAVE_CMPXCHG_DOUBLE);
         |                   ^~~~~~~~~~~~~~~~~~~~~~~~


vim +/KMALLOC_NOLOCK_SUPPORTED +22 include/linux/bpf_local_storage.h

    21	
  > 22	static const bool KMALLOC_NOLOCK_SUPPORTED = IS_ENABLED(CONFIG_HAVE_CMPXCHG_DOUBLE);
    23	

-- 
0-DAY CI Kernel Test Service
https://github.com/intel/lkp-tests/wiki

^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2026-03-14 17:06 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-03-14 10:36 [PATCH bpf] bpf: do not use kmalloc_nolock when !HAVE_CMPXCHG_DOUBLE Levi Zim via B4 Relay
2026-03-14 11:09 ` bot+bpf-ci
2026-03-14 15:17   ` Levi Zim
2026-03-14 17:05 ` kernel test robot

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox