aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndy Lutomirski <[email protected]>2014-12-03 15:37:08 -0800
committerLinus Torvalds <[email protected]>2014-12-03 20:55:58 -0800
commit7cc78f8fa02c2485104b86434acbc1538a3bd807 (patch)
treef3a9fdccb6f2c4db996299fe23f6597592b30085
parentebcd241a635c868b1f89abbfb4dd176ca5f81eba (diff)
context_tracking: Restore previous state in schedule_user
It appears that some SCHEDULE_USER (asm for schedule_user) callers in arch/x86/kernel/entry_64.S are called from RCU kernel context, and schedule_user will return in RCU user context. This causes RCU warnings and possible failures. This is intended to be a minimal fix suitable for 3.18. Reported-and-tested-by: Dave Jones <[email protected]> Cc: Oleg Nesterov <[email protected]> Cc: Frédéric Weisbecker <[email protected]> Acked-by: Paul E. McKenney <[email protected]> Signed-off-by: Andy Lutomirski <[email protected]> Signed-off-by: Linus Torvalds <[email protected]>
-rw-r--r--kernel/sched/core.c8
1 files changed, 6 insertions, 2 deletions
diff --git a/kernel/sched/core.c b/kernel/sched/core.c
index 24beb9bb4c3e..89e7283015a6 100644
--- a/kernel/sched/core.c
+++ b/kernel/sched/core.c
@@ -2874,10 +2874,14 @@ asmlinkage __visible void __sched schedule_user(void)
* or we have been woken up remotely but the IPI has not yet arrived,
* we haven't yet exited the RCU idle mode. Do it here manually until
* we find a better solution.
+ *
+ * NB: There are buggy callers of this function. Ideally we
+ * should warn if prev_state != IN_USER, but that will trigger
+ * too frequently to make sense yet.
*/
- user_exit();
+ enum ctx_state prev_state = exception_enter();
schedule();
- user_enter();
+ exception_exit(prev_state);
}
#endif