diff options
Diffstat (limited to 'arch/powerpc')
-rw-r--r-- | arch/powerpc/include/asm/mmu_context.h | 2 | ||||
-rw-r--r-- | arch/powerpc/mm/mmu_context_hash32.c | 29 |
2 files changed, 24 insertions, 7 deletions
diff --git a/arch/powerpc/include/asm/mmu_context.h b/arch/powerpc/include/asm/mmu_context.h index 26383e0778aa..81fb41289d6c 100644 --- a/arch/powerpc/include/asm/mmu_context.h +++ b/arch/powerpc/include/asm/mmu_context.h | |||
@@ -27,6 +27,8 @@ extern int __init_new_context(void); | |||
27 | extern void __destroy_context(int context_id); | 27 | extern void __destroy_context(int context_id); |
28 | static inline void mmu_context_init(void) { } | 28 | static inline void mmu_context_init(void) { } |
29 | #else | 29 | #else |
30 | extern unsigned long __init_new_context(void); | ||
31 | extern void __destroy_context(unsigned long context_id); | ||
30 | extern void mmu_context_init(void); | 32 | extern void mmu_context_init(void); |
31 | #endif | 33 | #endif |
32 | 34 | ||
diff --git a/arch/powerpc/mm/mmu_context_hash32.c b/arch/powerpc/mm/mmu_context_hash32.c index 0dfba2bf7f31..d0ee554e86e4 100644 --- a/arch/powerpc/mm/mmu_context_hash32.c +++ b/arch/powerpc/mm/mmu_context_hash32.c | |||
@@ -60,11 +60,7 @@ | |||
60 | static unsigned long next_mmu_context; | 60 | static unsigned long next_mmu_context; |
61 | static unsigned long context_map[LAST_CONTEXT / BITS_PER_LONG + 1]; | 61 | static unsigned long context_map[LAST_CONTEXT / BITS_PER_LONG + 1]; |
62 | 62 | ||
63 | 63 | unsigned long __init_new_context(void) | |
64 | /* | ||
65 | * Set up the context for a new address space. | ||
66 | */ | ||
67 | int init_new_context(struct task_struct *t, struct mm_struct *mm) | ||
68 | { | 64 | { |
69 | unsigned long ctx = next_mmu_context; | 65 | unsigned long ctx = next_mmu_context; |
70 | 66 | ||
@@ -74,19 +70,38 @@ int init_new_context(struct task_struct *t, struct mm_struct *mm) | |||
74 | ctx = 0; | 70 | ctx = 0; |
75 | } | 71 | } |
76 | next_mmu_context = (ctx + 1) & LAST_CONTEXT; | 72 | next_mmu_context = (ctx + 1) & LAST_CONTEXT; |
77 | mm->context.id = ctx; | 73 | |
74 | return ctx; | ||
75 | } | ||
76 | EXPORT_SYMBOL_GPL(__init_new_context); | ||
77 | |||
78 | /* | ||
79 | * Set up the context for a new address space. | ||
80 | */ | ||
81 | int init_new_context(struct task_struct *t, struct mm_struct *mm) | ||
82 | { | ||
83 | mm->context.id = __init_new_context(); | ||
78 | 84 | ||
79 | return 0; | 85 | return 0; |
80 | } | 86 | } |
81 | 87 | ||
82 | /* | 88 | /* |
89 | * Free a context ID. Make sure to call this with preempt disabled! | ||
90 | */ | ||
91 | void __destroy_context(unsigned long ctx) | ||
92 | { | ||
93 | clear_bit(ctx, context_map); | ||
94 | } | ||
95 | EXPORT_SYMBOL_GPL(__destroy_context); | ||
96 | |||
97 | /* | ||
83 | * We're finished using the context for an address space. | 98 | * We're finished using the context for an address space. |
84 | */ | 99 | */ |
85 | void destroy_context(struct mm_struct *mm) | 100 | void destroy_context(struct mm_struct *mm) |
86 | { | 101 | { |
87 | preempt_disable(); | 102 | preempt_disable(); |
88 | if (mm->context.id != NO_CONTEXT) { | 103 | if (mm->context.id != NO_CONTEXT) { |
89 | clear_bit(mm->context.id, context_map); | 104 | __destroy_context(mm->context.id); |
90 | mm->context.id = NO_CONTEXT; | 105 | mm->context.id = NO_CONTEXT; |
91 | } | 106 | } |
92 | preempt_enable(); | 107 | preempt_enable(); |