aboutsummaryrefslogtreecommitdiffstats
path: root/include
diff options
context:
space:
mode:
authorGuillaume Autran <gautran@mrv.com>2005-07-13 04:10:45 -0400
committerLinus Torvalds <torvalds@g5.osdl.org>2005-07-13 14:25:24 -0400
commitddca3b80cef36cc668f924ef5154a79acb19ebd7 (patch)
tree2cfb8ac6837682d975a1cb761360977ac54a6aef /include
parent88bd5121d635136e01369141367f315665534b3c (diff)
[PATCH] ppc32: fix destroy_context() race condition
Fix for a race condition when a task gets preempted by another task while executing the destroy_context(...) in a FEW_CONTEXTS environment. mm->context == NO_CONTEXT but the context_map may indicate all contexts are in use. The solution to this problem is to disable kernel preemption while destroying a MMU context. Signed-off-by: Guillaume Autran <gautran@mrv.com> Acked-by: Benjamin Herrenschmidt <benh@kernel.crashing.org> Signed-off-by: Andrew Morton <akpm@osdl.org> Signed-off-by: Linus Torvalds <torvalds@osdl.org>
Diffstat (limited to 'include')
-rw-r--r--include/asm-ppc/mmu_context.h2
1 files changed, 2 insertions, 0 deletions
diff --git a/include/asm-ppc/mmu_context.h b/include/asm-ppc/mmu_context.h
index ccabbce39d85..afe26ffc2e2d 100644
--- a/include/asm-ppc/mmu_context.h
+++ b/include/asm-ppc/mmu_context.h
@@ -149,6 +149,7 @@ static inline void get_mmu_context(struct mm_struct *mm)
149 */ 149 */
150static inline void destroy_context(struct mm_struct *mm) 150static inline void destroy_context(struct mm_struct *mm)
151{ 151{
152 preempt_disable();
152 if (mm->context != NO_CONTEXT) { 153 if (mm->context != NO_CONTEXT) {
153 clear_bit(mm->context, context_map); 154 clear_bit(mm->context, context_map);
154 mm->context = NO_CONTEXT; 155 mm->context = NO_CONTEXT;
@@ -156,6 +157,7 @@ static inline void destroy_context(struct mm_struct *mm)
156 atomic_inc(&nr_free_contexts); 157 atomic_inc(&nr_free_contexts);
157#endif 158#endif
158 } 159 }
160 preempt_enable();
159} 161}
160 162
161static inline void switch_mm(struct mm_struct *prev, struct mm_struct *next, 163static inline void switch_mm(struct mm_struct *prev, struct mm_struct *next,