aboutsummaryrefslogtreecommitdiffstats
path: root/arch/mips/kernel
diff options
context:
space:
mode:
authorSteven J. Hill <Steven.Hill@imgtec.com>2013-03-25 12:58:57 -0400
committerRalf Baechle <ralf@linux-mips.org>2013-05-08 06:30:10 -0400
commitd532f3d26716a39dfd4b88d687bd344fbe77e390 (patch)
tree64bb16ffd8176e0c9e692817b1d17df717c127ed /arch/mips/kernel
parent49bffbdc88fdd8f5eac40306a617252625a0fa35 (diff)
MIPS: Allow ASID size to be determined at boot time.
Original patch by Ralf Baechle and removed by Harold Koerfgen with commit f67e4ffc79905482c3b9b8c8dd65197bac7eb508. This allows for more generic kernels since the size of the ASID and corresponding masks can be determined at run-time. This patch is also required for the new Aptiv cores and has been tested on Malta and Malta Aptiv platforms. [ralf@linux-mips.org: Added relevant part of fix https://patchwork.linux-mips.org/patch/5213/] Signed-off-by: Steven J. Hill <Steven.Hill@imgtec.com> Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
Diffstat (limited to 'arch/mips/kernel')
-rw-r--r--arch/mips/kernel/genex.S2
-rw-r--r--arch/mips/kernel/smtc.c10
-rw-r--r--arch/mips/kernel/traps.c6
3 files changed, 10 insertions, 8 deletions
diff --git a/arch/mips/kernel/genex.S b/arch/mips/kernel/genex.S
index ecb347ce1b3d..5360b1db337d 100644
--- a/arch/mips/kernel/genex.S
+++ b/arch/mips/kernel/genex.S
@@ -480,7 +480,7 @@ NESTED(nmi_handler, PT_SIZE, sp)
480 .set noreorder 480 .set noreorder
481 /* check if TLB contains a entry for EPC */ 481 /* check if TLB contains a entry for EPC */
482 MFC0 k1, CP0_ENTRYHI 482 MFC0 k1, CP0_ENTRYHI
483 andi k1, 0xff /* ASID_MASK */ 483 andi k1, 0xff /* ASID_MASK patched at run-time!! */
484 MFC0 k0, CP0_EPC 484 MFC0 k0, CP0_EPC
485 PTR_SRL k0, _PAGE_SHIFT + 1 485 PTR_SRL k0, _PAGE_SHIFT + 1
486 PTR_SLL k0, _PAGE_SHIFT + 1 486 PTR_SLL k0, _PAGE_SHIFT + 1
diff --git a/arch/mips/kernel/smtc.c b/arch/mips/kernel/smtc.c
index 7186222dc5bb..31d22f3121c9 100644
--- a/arch/mips/kernel/smtc.c
+++ b/arch/mips/kernel/smtc.c
@@ -111,7 +111,7 @@ static int vpe0limit;
111static int ipibuffers; 111static int ipibuffers;
112static int nostlb; 112static int nostlb;
113static int asidmask; 113static int asidmask;
114unsigned long smtc_asid_mask = 0xff; 114unsigned int smtc_asid_mask = 0xff;
115 115
116static int __init vpe0tcs(char *str) 116static int __init vpe0tcs(char *str)
117{ 117{
@@ -1395,7 +1395,7 @@ void smtc_get_new_mmu_context(struct mm_struct *mm, unsigned long cpu)
1395 asid = asid_cache(cpu); 1395 asid = asid_cache(cpu);
1396 1396
1397 do { 1397 do {
1398 if (!((asid += ASID_INC) & ASID_MASK) ) { 1398 if (!ASID_MASK(ASID_INC(asid))) {
1399 if (cpu_has_vtag_icache) 1399 if (cpu_has_vtag_icache)
1400 flush_icache_all(); 1400 flush_icache_all();
1401 /* Traverse all online CPUs (hack requires contiguous range) */ 1401 /* Traverse all online CPUs (hack requires contiguous range) */
@@ -1414,7 +1414,7 @@ void smtc_get_new_mmu_context(struct mm_struct *mm, unsigned long cpu)
1414 mips_ihb(); 1414 mips_ihb();
1415 } 1415 }
1416 tcstat = read_tc_c0_tcstatus(); 1416 tcstat = read_tc_c0_tcstatus();
1417 smtc_live_asid[tlb][(tcstat & ASID_MASK)] |= (asiduse)(0x1 << i); 1417 smtc_live_asid[tlb][ASID_MASK(tcstat)] |= (asiduse)(0x1 << i);
1418 if (!prevhalt) 1418 if (!prevhalt)
1419 write_tc_c0_tchalt(0); 1419 write_tc_c0_tchalt(0);
1420 } 1420 }
@@ -1423,7 +1423,7 @@ void smtc_get_new_mmu_context(struct mm_struct *mm, unsigned long cpu)
1423 asid = ASID_FIRST_VERSION; 1423 asid = ASID_FIRST_VERSION;
1424 local_flush_tlb_all(); /* start new asid cycle */ 1424 local_flush_tlb_all(); /* start new asid cycle */
1425 } 1425 }
1426 } while (smtc_live_asid[tlb][(asid & ASID_MASK)]); 1426 } while (smtc_live_asid[tlb][ASID_MASK(asid)]);
1427 1427
1428 /* 1428 /*
1429 * SMTC shares the TLB within VPEs and possibly across all VPEs. 1429 * SMTC shares the TLB within VPEs and possibly across all VPEs.
@@ -1461,7 +1461,7 @@ void smtc_flush_tlb_asid(unsigned long asid)
1461 tlb_read(); 1461 tlb_read();
1462 ehb(); 1462 ehb();
1463 ehi = read_c0_entryhi(); 1463 ehi = read_c0_entryhi();
1464 if ((ehi & ASID_MASK) == asid) { 1464 if (ASID_MASK(ehi) == asid) {
1465 /* 1465 /*
1466 * Invalidate only entries with specified ASID, 1466 * Invalidate only entries with specified ASID,
1467 * makiing sure all entries differ. 1467 * makiing sure all entries differ.
diff --git a/arch/mips/kernel/traps.c b/arch/mips/kernel/traps.c
index c3abb88170fc..4b6b607b0179 100644
--- a/arch/mips/kernel/traps.c
+++ b/arch/mips/kernel/traps.c
@@ -1547,6 +1547,7 @@ void __cpuinit per_cpu_trap_init(bool is_boot_cpu)
1547 unsigned int cpu = smp_processor_id(); 1547 unsigned int cpu = smp_processor_id();
1548 unsigned int status_set = ST0_CU0; 1548 unsigned int status_set = ST0_CU0;
1549 unsigned int hwrena = cpu_hwrena_impl_bits; 1549 unsigned int hwrena = cpu_hwrena_impl_bits;
1550 unsigned long asid = 0;
1550#ifdef CONFIG_MIPS_MT_SMTC 1551#ifdef CONFIG_MIPS_MT_SMTC
1551 int secondaryTC = 0; 1552 int secondaryTC = 0;
1552 int bootTC = (cpu == 0); 1553 int bootTC = (cpu == 0);
@@ -1630,8 +1631,9 @@ void __cpuinit per_cpu_trap_init(bool is_boot_cpu)
1630 } 1631 }
1631#endif /* CONFIG_MIPS_MT_SMTC */ 1632#endif /* CONFIG_MIPS_MT_SMTC */
1632 1633
1633 if (!cpu_data[cpu].asid_cache) 1634 asid = ASID_FIRST_VERSION;
1634 cpu_data[cpu].asid_cache = ASID_FIRST_VERSION; 1635 cpu_data[cpu].asid_cache = asid;
1636 TLBMISS_HANDLER_SETUP();
1635 1637
1636 atomic_inc(&init_mm.mm_count); 1638 atomic_inc(&init_mm.mm_count);
1637 current->active_mm = &init_mm; 1639 current->active_mm = &init_mm;