diff options
-rw-r--r-- | arch/powerpc/mm/hash_utils_64.c | 23 | ||||
-rw-r--r-- | arch/powerpc/platforms/pseries/lpar.c | 15 | ||||
-rw-r--r-- | include/asm-powerpc/machdep.h | 2 | ||||
-rw-r--r-- | include/asm-powerpc/sparsemem.h | 1 |
4 files changed, 41 insertions, 0 deletions
diff --git a/arch/powerpc/mm/hash_utils_64.c b/arch/powerpc/mm/hash_utils_64.c index 73b78486abfc..4cc53f92377e 100644 --- a/arch/powerpc/mm/hash_utils_64.c +++ b/arch/powerpc/mm/hash_utils_64.c | |||
@@ -192,6 +192,24 @@ int htab_bolt_mapping(unsigned long vstart, unsigned long vend, | |||
192 | return ret < 0 ? ret : 0; | 192 | return ret < 0 ? ret : 0; |
193 | } | 193 | } |
194 | 194 | ||
195 | static void htab_remove_mapping(unsigned long vstart, unsigned long vend, | ||
196 | int psize, int ssize) | ||
197 | { | ||
198 | unsigned long vaddr; | ||
199 | unsigned int step, shift; | ||
200 | |||
201 | shift = mmu_psize_defs[psize].shift; | ||
202 | step = 1 << shift; | ||
203 | |||
204 | if (!ppc_md.hpte_removebolted) { | ||
205 | printk("Sub-arch doesn't implement hpte_removebolted\n"); | ||
206 | return; | ||
207 | } | ||
208 | |||
209 | for (vaddr = vstart; vaddr < vend; vaddr += step) | ||
210 | ppc_md.hpte_removebolted(vaddr, psize, ssize); | ||
211 | } | ||
212 | |||
195 | static int __init htab_dt_scan_seg_sizes(unsigned long node, | 213 | static int __init htab_dt_scan_seg_sizes(unsigned long node, |
196 | const char *uname, int depth, | 214 | const char *uname, int depth, |
197 | void *data) | 215 | void *data) |
@@ -430,6 +448,11 @@ void create_section_mapping(unsigned long start, unsigned long end) | |||
430 | _PAGE_ACCESSED | _PAGE_DIRTY | _PAGE_COHERENT | PP_RWXX, | 448 | _PAGE_ACCESSED | _PAGE_DIRTY | _PAGE_COHERENT | PP_RWXX, |
431 | mmu_linear_psize, mmu_kernel_ssize)); | 449 | mmu_linear_psize, mmu_kernel_ssize)); |
432 | } | 450 | } |
451 | |||
452 | void remove_section_mapping(unsigned long start, unsigned long end) | ||
453 | { | ||
454 | htab_remove_mapping(start, end, mmu_linear_psize, mmu_kernel_ssize); | ||
455 | } | ||
433 | #endif /* CONFIG_MEMORY_HOTPLUG */ | 456 | #endif /* CONFIG_MEMORY_HOTPLUG */ |
434 | 457 | ||
435 | static inline void make_bl(unsigned int *insn_addr, void *func) | 458 | static inline void make_bl(unsigned int *insn_addr, void *func) |
diff --git a/arch/powerpc/platforms/pseries/lpar.c b/arch/powerpc/platforms/pseries/lpar.c index 9a455d46379d..233d9be25f49 100644 --- a/arch/powerpc/platforms/pseries/lpar.c +++ b/arch/powerpc/platforms/pseries/lpar.c | |||
@@ -520,6 +520,20 @@ static void pSeries_lpar_hpte_invalidate(unsigned long slot, unsigned long va, | |||
520 | BUG_ON(lpar_rc != H_SUCCESS); | 520 | BUG_ON(lpar_rc != H_SUCCESS); |
521 | } | 521 | } |
522 | 522 | ||
523 | static void pSeries_lpar_hpte_removebolted(unsigned long ea, | ||
524 | int psize, int ssize) | ||
525 | { | ||
526 | unsigned long slot, vsid, va; | ||
527 | |||
528 | vsid = get_kernel_vsid(ea, ssize); | ||
529 | va = hpt_va(ea, vsid, ssize); | ||
530 | |||
531 | slot = pSeries_lpar_hpte_find(va, psize, ssize); | ||
532 | BUG_ON(slot == -1); | ||
533 | |||
534 | pSeries_lpar_hpte_invalidate(slot, va, psize, ssize, 0); | ||
535 | } | ||
536 | |||
523 | /* Flag bits for H_BULK_REMOVE */ | 537 | /* Flag bits for H_BULK_REMOVE */ |
524 | #define HBR_REQUEST 0x4000000000000000UL | 538 | #define HBR_REQUEST 0x4000000000000000UL |
525 | #define HBR_RESPONSE 0x8000000000000000UL | 539 | #define HBR_RESPONSE 0x8000000000000000UL |
@@ -597,6 +611,7 @@ void __init hpte_init_lpar(void) | |||
597 | ppc_md.hpte_updateboltedpp = pSeries_lpar_hpte_updateboltedpp; | 611 | ppc_md.hpte_updateboltedpp = pSeries_lpar_hpte_updateboltedpp; |
598 | ppc_md.hpte_insert = pSeries_lpar_hpte_insert; | 612 | ppc_md.hpte_insert = pSeries_lpar_hpte_insert; |
599 | ppc_md.hpte_remove = pSeries_lpar_hpte_remove; | 613 | ppc_md.hpte_remove = pSeries_lpar_hpte_remove; |
614 | ppc_md.hpte_removebolted = pSeries_lpar_hpte_removebolted; | ||
600 | ppc_md.flush_hash_range = pSeries_lpar_flush_hash_range; | 615 | ppc_md.flush_hash_range = pSeries_lpar_flush_hash_range; |
601 | ppc_md.hpte_clear_all = pSeries_lpar_hptab_clear; | 616 | ppc_md.hpte_clear_all = pSeries_lpar_hptab_clear; |
602 | } | 617 | } |
diff --git a/include/asm-powerpc/machdep.h b/include/asm-powerpc/machdep.h index 0872ec228c1e..b95386aed50d 100644 --- a/include/asm-powerpc/machdep.h +++ b/include/asm-powerpc/machdep.h | |||
@@ -68,6 +68,8 @@ struct machdep_calls { | |||
68 | unsigned long vflags, | 68 | unsigned long vflags, |
69 | int psize, int ssize); | 69 | int psize, int ssize); |
70 | long (*hpte_remove)(unsigned long hpte_group); | 70 | long (*hpte_remove)(unsigned long hpte_group); |
71 | void (*hpte_removebolted)(unsigned long ea, | ||
72 | int psize, int ssize); | ||
71 | void (*flush_hash_range)(unsigned long number, int local); | 73 | void (*flush_hash_range)(unsigned long number, int local); |
72 | 74 | ||
73 | /* special for kexec, to be called in real mode, linar mapping is | 75 | /* special for kexec, to be called in real mode, linar mapping is |
diff --git a/include/asm-powerpc/sparsemem.h b/include/asm-powerpc/sparsemem.h index e8b493d52b4f..c5acf4ccf571 100644 --- a/include/asm-powerpc/sparsemem.h +++ b/include/asm-powerpc/sparsemem.h | |||
@@ -15,6 +15,7 @@ | |||
15 | 15 | ||
16 | #ifdef CONFIG_MEMORY_HOTPLUG | 16 | #ifdef CONFIG_MEMORY_HOTPLUG |
17 | extern void create_section_mapping(unsigned long start, unsigned long end); | 17 | extern void create_section_mapping(unsigned long start, unsigned long end); |
18 | extern void remove_section_mapping(unsigned long start, unsigned long end); | ||
18 | #ifdef CONFIG_NUMA | 19 | #ifdef CONFIG_NUMA |
19 | extern int hot_add_scn_to_nid(unsigned long scn_addr); | 20 | extern int hot_add_scn_to_nid(unsigned long scn_addr); |
20 | #else | 21 | #else |