summaryrefslogtreecommitdiff
path: root/include
diff options
context:
space:
mode:
authorDavid Stevens <stevensd@google.com>2026-09-04 10:31:45 -0700
committerAndrew Morton <akpm@linux-foundation.org>2026-09-29 23:12:27 -0700
commit01b0c80d45cb7df9ddbcd3e1710d0bf21febc4f3 (patch)
tree708706b8440fa11d9b4b24703ac9888e37761dca /include
parentc26093329ecbf88c2291b323c9e52d46b8d281fb (diff)
downloadlinux-next-01b0c80d45cb7df9ddbcd3e1710d0bf21febc4f3.tar.gz
linux-next-01b0c80d45cb7df9ddbcd3e1710d0bf21febc4f3.zip
memcg: don't call schedule_work when no spinning is allowed
Memcg charging can be done from any context, but calling schedule_work() isn't safe from an NMI. If memory.high is breached from a context where spinning isn't allowed, use irq_work to schedule the reclaim work. Found this via code inspection. I spent a little bit trying to trigger it for real, but the only way I managed was by writing a hacky driver absuing alloc_pages_nolock(). Link: https://lore.kernel.org/20260904173145.2028377-1-stevensd@google.com Fixes: 3ac4638a734a ("memcg: make memcg_rstat_updated nmi safe") Signed-off-by: David Stevens <stevensd@google.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Acked-by: Michal Hocko <mhocko@suse.com> Reviewed-by: Johannes Weiner <hannes@cmpxchg.org> Acked-by: Shakeel Butt <shakeel.butt@linux.dev> Cc: Lorenzo Stoakes <ljs@kernel.org> Cc: Muchun Song <muchun.song@linux.dev> Cc: Roman Gushchin <roman.gushchin@linux.dev>
Diffstat (limited to 'include')
-rw-r--r--include/linux/memcontrol.h2
1 files changed, 2 insertions, 0 deletions
diff --git a/include/linux/memcontrol.h b/include/linux/memcontrol.h
index c0c9805b6f03..4f720791a31c 100644
--- a/include/linux/memcontrol.h
+++ b/include/linux/memcontrol.h
@@ -23,6 +23,7 @@
#include <linux/writeback.h>
#include <linux/page-flags.h>
#include <linux/shrinker.h>
+#include <linux/irq_work_types.h>
struct mem_cgroup;
struct obj_cgroup;
@@ -233,6 +234,7 @@ struct mem_cgroup {
#endif
/* Range enforcement for interrupt charges */
+ struct irq_work high_irq_work;
struct work_struct high_work;
__cacheline_group_end_aligned(memcg_write_hot);