From 87405282a9f01fba612babb5bb4c3683db150a6b Mon Sep 17 00:00:00 2001 From: Ben Hutchings Date: Mon, 6 Jul 2020 01:35:06 +0100 Subject: [PATCH] [rt] Drop idle task related parts of "sched: Move mmdrop to RCU on RT" This conflicted with and seems to be redundant with "sched/core: Fix illegal RCU from offline CPUs". I think the previous resolution of this conflict can result in a double free. --- debian/changelog | 4 +- .../0107-sched-Move-mmdrop-to-RCU-on-RT.patch | 40 ++----------------- 2 files changed, 6 insertions(+), 38 deletions(-) diff --git a/debian/changelog b/debian/changelog index 9c23ecaf8..f33020829 100644 --- a/debian/changelog +++ b/debian/changelog @@ -1005,14 +1005,14 @@ linux (4.19.131-1) UNRELEASED; urgency=medium - fs/dcache: Include swait.h header - mm: slub: Always flush the delayed empty slubs in flush_all() - tasklet: Fix UP case for tasklet CHAINED state - * [rt] Refresh "sched: Move mmdrop to RCU on RT" for context changes in - 4.19.129 [ Ben Hutchings ] * [rt] Update "net: move xmit_recursion to per-task variable on -RT" to apply on top of "net: place xmit recursion in softnet data" * [rt] Drop "net: Add a mutex around devnet_rename_seq", redundant with "net: Introduce net_rwsem to protect net_namespace_list" + * [rt] Drop idle task related parts of "sched: Move mmdrop to RCU on RT", + redundant with "sched/core: Fix illegal RCU from offline CPUs" -- Salvatore Bonaccorso Wed, 13 May 2020 17:44:43 +0200 diff --git a/debian/patches-rt/0107-sched-Move-mmdrop-to-RCU-on-RT.patch b/debian/patches-rt/0107-sched-Move-mmdrop-to-RCU-on-RT.patch index 4cb14bbc8..01744aef6 100644 --- a/debian/patches-rt/0107-sched-Move-mmdrop-to-RCU-on-RT.patch +++ b/debian/patches-rt/0107-sched-Move-mmdrop-to-RCU-on-RT.patch @@ -28,7 +28,7 @@ Signed-off-by: Thomas Gleixner #include #include -@@ -489,6 +490,9 @@ +@@ -489,6 +490,9 @@ struct mm_struct { bool tlb_flush_batched; #endif struct uprobes_state uprobes_state; @@ -40,7 +40,7 @@ Signed-off-by: Thomas Gleixner #endif --- a/include/linux/sched/mm.h +++ b/include/linux/sched/mm.h -@@ -51,6 +51,17 @@ +@@ -51,6 +51,17 @@ static inline void mmdrop(struct mm_stru void mmdrop(struct mm_struct *mm); @@ -60,7 +60,7 @@ Signed-off-by: Thomas Gleixner * followed by taking the mmap_sem for writing before modifying the --- a/kernel/fork.c +++ b/kernel/fork.c -@@ -647,6 +647,19 @@ +@@ -647,6 +647,19 @@ void __mmdrop(struct mm_struct *mm) } EXPORT_SYMBOL_GPL(__mmdrop); @@ -82,7 +82,7 @@ Signed-off-by: Thomas Gleixner struct mm_struct *mm; --- a/kernel/sched/core.c +++ b/kernel/sched/core.c -@@ -2729,9 +2729,13 @@ +@@ -2729,9 +2729,13 @@ static struct rq *finish_task_switch(str * provided by mmdrop(), * - a sync_core for SYNC_CORE. */ @@ -97,35 +97,3 @@ Signed-off-by: Thomas Gleixner } if (unlikely(prev_state == TASK_DEAD)) { if (prev->sched_class->task_dead) -@@ -5602,6 +5606,8 @@ - #endif /* CONFIG_NUMA_BALANCING */ - - #ifdef CONFIG_HOTPLUG_CPU -+static DEFINE_PER_CPU(struct mm_struct *, idle_last_mm); -+ - /* - * Ensure that the idle task is using init_mm right before its CPU goes - * offline. -@@ -5617,6 +5623,11 @@ - switch_mm(mm, &init_mm, current); - finish_arch_post_lock_switch(); - } -+ /* -+ * Defer the cleanup to an alive cpu. On RT we can neither -+ * call mmdrop() nor mmdrop_delayed() from here. -+ */ -+ per_cpu(idle_last_mm, smp_processor_id()) = mm; - - /* finish_cpu(), as ran on the BP, will clean up the active_mm state */ - } -@@ -5930,6 +5941,10 @@ - update_max_interval(); - nohz_balance_exit_idle(rq); - hrtick_clear(rq); -+ if (per_cpu(idle_last_mm, cpu)) { -+ mmdrop_delayed(per_cpu(idle_last_mm, cpu)); -+ per_cpu(idle_last_mm, cpu) = NULL; -+ } - return 0; - } - #endif