aboutsummaryrefslogtreecommitdiffstats
path: root/arch/sparc
diff options
context:
space:
mode:
Diffstat (limited to 'arch/sparc')
-rw-r--r--arch/sparc/include/asm/page_64.h1
-rw-r--r--arch/sparc/include/asm/smp_64.h2
-rw-r--r--arch/sparc/kernel/setup_64.c26
-rw-r--r--arch/sparc/kernel/smp_64.c14
-rw-r--r--arch/sparc/mm/fault_64.c1
-rw-r--r--arch/sparc/mm/init_64.c22
-rw-r--r--arch/sparc/mm/tlb.c35
-rw-r--r--arch/sparc/mm/tsb.c18
8 files changed, 90 insertions, 29 deletions
diff --git a/arch/sparc/include/asm/page_64.h b/arch/sparc/include/asm/page_64.h
index 8c2a8c937540..c1263fc390db 100644
--- a/arch/sparc/include/asm/page_64.h
+++ b/arch/sparc/include/asm/page_64.h
@@ -25,6 +25,7 @@
25#define HPAGE_MASK (~(HPAGE_SIZE - 1UL)) 25#define HPAGE_MASK (~(HPAGE_SIZE - 1UL))
26#define HUGETLB_PAGE_ORDER (HPAGE_SHIFT - PAGE_SHIFT) 26#define HUGETLB_PAGE_ORDER (HPAGE_SHIFT - PAGE_SHIFT)
27#define HAVE_ARCH_HUGETLB_UNMAPPED_AREA 27#define HAVE_ARCH_HUGETLB_UNMAPPED_AREA
28#define REAL_HPAGE_PER_HPAGE (_AC(1,UL) << (HPAGE_SHIFT - REAL_HPAGE_SHIFT))
28#endif 29#endif
29 30
30#ifndef __ASSEMBLY__ 31#ifndef __ASSEMBLY__
diff --git a/arch/sparc/include/asm/smp_64.h b/arch/sparc/include/asm/smp_64.h
index 26d9e7726867..ce2233f7e662 100644
--- a/arch/sparc/include/asm/smp_64.h
+++ b/arch/sparc/include/asm/smp_64.h
@@ -43,6 +43,7 @@ void arch_send_call_function_ipi_mask(const struct cpumask *mask);
43int hard_smp_processor_id(void); 43int hard_smp_processor_id(void);
44#define raw_smp_processor_id() (current_thread_info()->cpu) 44#define raw_smp_processor_id() (current_thread_info()->cpu)
45 45
46void smp_fill_in_cpu_possible_map(void);
46void smp_fill_in_sib_core_maps(void); 47void smp_fill_in_sib_core_maps(void);
47void cpu_play_dead(void); 48void cpu_play_dead(void);
48 49
@@ -72,6 +73,7 @@ void __cpu_die(unsigned int cpu);
72#define smp_fill_in_sib_core_maps() do { } while (0) 73#define smp_fill_in_sib_core_maps() do { } while (0)
73#define smp_fetch_global_regs() do { } while (0) 74#define smp_fetch_global_regs() do { } while (0)
74#define smp_fetch_global_pmu() do { } while (0) 75#define smp_fetch_global_pmu() do { } while (0)
76#define smp_fill_in_cpu_possible_map() do { } while (0)
75 77
76#endif /* !(CONFIG_SMP) */ 78#endif /* !(CONFIG_SMP) */
77 79
diff --git a/arch/sparc/kernel/setup_64.c b/arch/sparc/kernel/setup_64.c
index 599f1207eed2..6b7331d198e9 100644
--- a/arch/sparc/kernel/setup_64.c
+++ b/arch/sparc/kernel/setup_64.c
@@ -31,6 +31,7 @@
31#include <linux/initrd.h> 31#include <linux/initrd.h>
32#include <linux/module.h> 32#include <linux/module.h>
33#include <linux/start_kernel.h> 33#include <linux/start_kernel.h>
34#include <linux/bootmem.h>
34 35
35#include <asm/io.h> 36#include <asm/io.h>
36#include <asm/processor.h> 37#include <asm/processor.h>
@@ -50,6 +51,8 @@
50#include <asm/elf.h> 51#include <asm/elf.h>
51#include <asm/mdesc.h> 52#include <asm/mdesc.h>
52#include <asm/cacheflush.h> 53#include <asm/cacheflush.h>
54#include <asm/dma.h>
55#include <asm/irq.h>
53 56
54#ifdef CONFIG_IP_PNP 57#ifdef CONFIG_IP_PNP
55#include <net/ipconfig.h> 58#include <net/ipconfig.h>
@@ -590,6 +593,22 @@ static void __init init_sparc64_elf_hwcap(void)
590 pause_patch(); 593 pause_patch();
591} 594}
592 595
596void __init alloc_irqstack_bootmem(void)
597{
598 unsigned int i, node;
599
600 for_each_possible_cpu(i) {
601 node = cpu_to_node(i);
602
603 softirq_stack[i] = __alloc_bootmem_node(NODE_DATA(node),
604 THREAD_SIZE,
605 THREAD_SIZE, 0);
606 hardirq_stack[i] = __alloc_bootmem_node(NODE_DATA(node),
607 THREAD_SIZE,
608 THREAD_SIZE, 0);
609 }
610}
611
593void __init setup_arch(char **cmdline_p) 612void __init setup_arch(char **cmdline_p)
594{ 613{
595 /* Initialize PROM console and command line. */ 614 /* Initialize PROM console and command line. */
@@ -650,6 +669,13 @@ void __init setup_arch(char **cmdline_p)
650 669
651 paging_init(); 670 paging_init();
652 init_sparc64_elf_hwcap(); 671 init_sparc64_elf_hwcap();
672 smp_fill_in_cpu_possible_map();
673 /*
674 * Once the OF device tree and MDESC have been setup and nr_cpus has
675 * been parsed, we know the list of possible cpus. Therefore we can
676 * allocate the IRQ stacks.
677 */
678 alloc_irqstack_bootmem();
653} 679}
654 680
655extern int stop_a_enabled; 681extern int stop_a_enabled;
diff --git a/arch/sparc/kernel/smp_64.c b/arch/sparc/kernel/smp_64.c
index 8a6151a628ce..d3035ba6cd31 100644
--- a/arch/sparc/kernel/smp_64.c
+++ b/arch/sparc/kernel/smp_64.c
@@ -1227,6 +1227,20 @@ void __init smp_setup_processor_id(void)
1227 xcall_deliver_impl = hypervisor_xcall_deliver; 1227 xcall_deliver_impl = hypervisor_xcall_deliver;
1228} 1228}
1229 1229
1230void __init smp_fill_in_cpu_possible_map(void)
1231{
1232 int possible_cpus = num_possible_cpus();
1233 int i;
1234
1235 if (possible_cpus > nr_cpu_ids)
1236 possible_cpus = nr_cpu_ids;
1237
1238 for (i = 0; i < possible_cpus; i++)
1239 set_cpu_possible(i, true);
1240 for (; i < NR_CPUS; i++)
1241 set_cpu_possible(i, false);
1242}
1243
1230void smp_fill_in_sib_core_maps(void) 1244void smp_fill_in_sib_core_maps(void)
1231{ 1245{
1232 unsigned int i; 1246 unsigned int i;
diff --git a/arch/sparc/mm/fault_64.c b/arch/sparc/mm/fault_64.c
index e16fdd28a931..3f291d8c57f7 100644
--- a/arch/sparc/mm/fault_64.c
+++ b/arch/sparc/mm/fault_64.c
@@ -484,6 +484,7 @@ good_area:
484 tsb_grow(mm, MM_TSB_BASE, mm_rss); 484 tsb_grow(mm, MM_TSB_BASE, mm_rss);
485#if defined(CONFIG_HUGETLB_PAGE) || defined(CONFIG_TRANSPARENT_HUGEPAGE) 485#if defined(CONFIG_HUGETLB_PAGE) || defined(CONFIG_TRANSPARENT_HUGEPAGE)
486 mm_rss = mm->context.hugetlb_pte_count + mm->context.thp_pte_count; 486 mm_rss = mm->context.hugetlb_pte_count + mm->context.thp_pte_count;
487 mm_rss *= REAL_HPAGE_PER_HPAGE;
487 if (unlikely(mm_rss > 488 if (unlikely(mm_rss >
488 mm->context.tsb_block[MM_TSB_HUGE].tsb_rss_limit)) { 489 mm->context.tsb_block[MM_TSB_HUGE].tsb_rss_limit)) {
489 if (mm->context.tsb_block[MM_TSB_HUGE].tsb) 490 if (mm->context.tsb_block[MM_TSB_HUGE].tsb)
diff --git a/arch/sparc/mm/init_64.c b/arch/sparc/mm/init_64.c
index 65457c9f1365..7ac6b62fb7c1 100644
--- a/arch/sparc/mm/init_64.c
+++ b/arch/sparc/mm/init_64.c
@@ -1160,7 +1160,7 @@ int __node_distance(int from, int to)
1160 return numa_latency[from][to]; 1160 return numa_latency[from][to];
1161} 1161}
1162 1162
1163static int find_best_numa_node_for_mlgroup(struct mdesc_mlgroup *grp) 1163static int __init find_best_numa_node_for_mlgroup(struct mdesc_mlgroup *grp)
1164{ 1164{
1165 int i; 1165 int i;
1166 1166
@@ -1173,8 +1173,8 @@ static int find_best_numa_node_for_mlgroup(struct mdesc_mlgroup *grp)
1173 return i; 1173 return i;
1174} 1174}
1175 1175
1176static void find_numa_latencies_for_group(struct mdesc_handle *md, u64 grp, 1176static void __init find_numa_latencies_for_group(struct mdesc_handle *md,
1177 int index) 1177 u64 grp, int index)
1178{ 1178{
1179 u64 arc; 1179 u64 arc;
1180 1180
@@ -2081,7 +2081,6 @@ void __init paging_init(void)
2081{ 2081{
2082 unsigned long end_pfn, shift, phys_base; 2082 unsigned long end_pfn, shift, phys_base;
2083 unsigned long real_end, i; 2083 unsigned long real_end, i;
2084 int node;
2085 2084
2086 setup_page_offset(); 2085 setup_page_offset();
2087 2086
@@ -2250,21 +2249,6 @@ void __init paging_init(void)
2250 /* Setup bootmem... */ 2249 /* Setup bootmem... */
2251 last_valid_pfn = end_pfn = bootmem_init(phys_base); 2250 last_valid_pfn = end_pfn = bootmem_init(phys_base);
2252 2251
2253 /* Once the OF device tree and MDESC have been setup, we know
2254 * the list of possible cpus. Therefore we can allocate the
2255 * IRQ stacks.
2256 */
2257 for_each_possible_cpu(i) {
2258 node = cpu_to_node(i);
2259
2260 softirq_stack[i] = __alloc_bootmem_node(NODE_DATA(node),
2261 THREAD_SIZE,
2262 THREAD_SIZE, 0);
2263 hardirq_stack[i] = __alloc_bootmem_node(NODE_DATA(node),
2264 THREAD_SIZE,
2265 THREAD_SIZE, 0);
2266 }
2267
2268 kernel_physical_mapping_init(); 2252 kernel_physical_mapping_init();
2269 2253
2270 { 2254 {
diff --git a/arch/sparc/mm/tlb.c b/arch/sparc/mm/tlb.c
index 3659d37b4d81..c56a195c9071 100644
--- a/arch/sparc/mm/tlb.c
+++ b/arch/sparc/mm/tlb.c
@@ -174,10 +174,25 @@ void set_pmd_at(struct mm_struct *mm, unsigned long addr,
174 return; 174 return;
175 175
176 if ((pmd_val(pmd) ^ pmd_val(orig)) & _PAGE_PMD_HUGE) { 176 if ((pmd_val(pmd) ^ pmd_val(orig)) & _PAGE_PMD_HUGE) {
177 if (pmd_val(pmd) & _PAGE_PMD_HUGE) 177 /*
178 mm->context.thp_pte_count++; 178 * Note that this routine only sets pmds for THP pages.
179 else 179 * Hugetlb pages are handled elsewhere. We need to check
180 mm->context.thp_pte_count--; 180 * for huge zero page. Huge zero pages are like hugetlb
181 * pages in that there is no RSS, but there is the need
182 * for TSB entries. So, huge zero page counts go into
183 * hugetlb_pte_count.
184 */
185 if (pmd_val(pmd) & _PAGE_PMD_HUGE) {
186 if (is_huge_zero_page(pmd_page(pmd)))
187 mm->context.hugetlb_pte_count++;
188 else
189 mm->context.thp_pte_count++;
190 } else {
191 if (is_huge_zero_page(pmd_page(orig)))
192 mm->context.hugetlb_pte_count--;
193 else
194 mm->context.thp_pte_count--;
195 }
181 196
182 /* Do not try to allocate the TSB hash table if we 197 /* Do not try to allocate the TSB hash table if we
183 * don't have one already. We have various locks held 198 * don't have one already. We have various locks held
@@ -204,6 +219,9 @@ void set_pmd_at(struct mm_struct *mm, unsigned long addr,
204 } 219 }
205} 220}
206 221
222/*
223 * This routine is only called when splitting a THP
224 */
207void pmdp_invalidate(struct vm_area_struct *vma, unsigned long address, 225void pmdp_invalidate(struct vm_area_struct *vma, unsigned long address,
208 pmd_t *pmdp) 226 pmd_t *pmdp)
209{ 227{
@@ -213,6 +231,15 @@ void pmdp_invalidate(struct vm_area_struct *vma, unsigned long address,
213 231
214 set_pmd_at(vma->vm_mm, address, pmdp, entry); 232 set_pmd_at(vma->vm_mm, address, pmdp, entry);
215 flush_tlb_range(vma, address, address + HPAGE_PMD_SIZE); 233 flush_tlb_range(vma, address, address + HPAGE_PMD_SIZE);
234
235 /*
236 * set_pmd_at() will not be called in a way to decrement
237 * thp_pte_count when splitting a THP, so do it now.
238 * Sanity check pmd before doing the actual decrement.
239 */
240 if ((pmd_val(entry) & _PAGE_PMD_HUGE) &&
241 !is_huge_zero_page(pmd_page(entry)))
242 (vma->vm_mm)->context.thp_pte_count--;
216} 243}
217 244
218void pgtable_trans_huge_deposit(struct mm_struct *mm, pmd_t *pmdp, 245void pgtable_trans_huge_deposit(struct mm_struct *mm, pmd_t *pmdp,
diff --git a/arch/sparc/mm/tsb.c b/arch/sparc/mm/tsb.c
index 6725ed45580e..f2b77112e9d8 100644
--- a/arch/sparc/mm/tsb.c
+++ b/arch/sparc/mm/tsb.c
@@ -469,8 +469,10 @@ retry_tsb_alloc:
469 469
470int init_new_context(struct task_struct *tsk, struct mm_struct *mm) 470int init_new_context(struct task_struct *tsk, struct mm_struct *mm)
471{ 471{
472 unsigned long mm_rss = get_mm_rss(mm);
472#if defined(CONFIG_HUGETLB_PAGE) || defined(CONFIG_TRANSPARENT_HUGEPAGE) 473#if defined(CONFIG_HUGETLB_PAGE) || defined(CONFIG_TRANSPARENT_HUGEPAGE)
473 unsigned long total_huge_pte_count; 474 unsigned long saved_hugetlb_pte_count;
475 unsigned long saved_thp_pte_count;
474#endif 476#endif
475 unsigned int i; 477 unsigned int i;
476 478
@@ -483,10 +485,12 @@ int init_new_context(struct task_struct *tsk, struct mm_struct *mm)
483 * will re-increment the counters as the parent PTEs are 485 * will re-increment the counters as the parent PTEs are
484 * copied into the child address space. 486 * copied into the child address space.
485 */ 487 */
486 total_huge_pte_count = mm->context.hugetlb_pte_count + 488 saved_hugetlb_pte_count = mm->context.hugetlb_pte_count;
487 mm->context.thp_pte_count; 489 saved_thp_pte_count = mm->context.thp_pte_count;
488 mm->context.hugetlb_pte_count = 0; 490 mm->context.hugetlb_pte_count = 0;
489 mm->context.thp_pte_count = 0; 491 mm->context.thp_pte_count = 0;
492
493 mm_rss -= saved_thp_pte_count * (HPAGE_SIZE / PAGE_SIZE);
490#endif 494#endif
491 495
492 /* copy_mm() copies over the parent's mm_struct before calling 496 /* copy_mm() copies over the parent's mm_struct before calling
@@ -499,11 +503,13 @@ int init_new_context(struct task_struct *tsk, struct mm_struct *mm)
499 /* If this is fork, inherit the parent's TSB size. We would 503 /* If this is fork, inherit the parent's TSB size. We would
500 * grow it to that size on the first page fault anyways. 504 * grow it to that size on the first page fault anyways.
501 */ 505 */
502 tsb_grow(mm, MM_TSB_BASE, get_mm_rss(mm)); 506 tsb_grow(mm, MM_TSB_BASE, mm_rss);
503 507
504#if defined(CONFIG_HUGETLB_PAGE) || defined(CONFIG_TRANSPARENT_HUGEPAGE) 508#if defined(CONFIG_HUGETLB_PAGE) || defined(CONFIG_TRANSPARENT_HUGEPAGE)
505 if (unlikely(total_huge_pte_count)) 509 if (unlikely(saved_hugetlb_pte_count + saved_thp_pte_count))
506 tsb_grow(mm, MM_TSB_HUGE, total_huge_pte_count); 510 tsb_grow(mm, MM_TSB_HUGE,
511 (saved_hugetlb_pte_count + saved_thp_pte_count) *
512 REAL_HPAGE_PER_HPAGE);
507#endif 513#endif
508 514
509 if (unlikely(!mm->context.tsb_block[MM_TSB_BASE].tsb)) 515 if (unlikely(!mm->context.tsb_block[MM_TSB_BASE].tsb))