mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
* [PATCH] MIPS: mm: tlb-r4k: Uniquify TLB entries on init
@ 2025-06-05 10:02 Jiaxun Yang
  2025-06-06 13:30 ` Jiaxun Yang
  2025-06-07  2:48 ` Maciej W. Rozycki
  0 siblings, 2 replies; 4+ messages in thread
From: Jiaxun Yang @ 2025-06-05 10:02 UTC (permalink / raw)
  To: Thomas Bogendoerfer; +Cc: linux-mips, linux-kernel, stable, Jiaxun Yang

Hardware or bootloader will initialize TLB entries to any value, which
may collide with kernel's UNIQUE_ENTRYHI value. On MIPS microAptiv/M5150
family of cores this will trigger machine check exception and cause boot
failure. On M5150 simulation this could happen 7 times out of 1000 boots.

Replace local_flush_tlb_all() with r4k_tlb_uniquify() which probes each
TLB ENTRIHI unique value for collisions before it's written and overwrites
any conflicting entries with safe values before initializing the kernel's
UNIQUE_ENTRYHI pattern.

Cc: stable@kernel.org
Signed-off-by: Jiaxun Yang <jiaxun.yang@flygoat.com>
---
 arch/mips/mm/tlb-r4k.c | 78 +++++++++++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 77 insertions(+), 1 deletion(-)

diff --git a/arch/mips/mm/tlb-r4k.c b/arch/mips/mm/tlb-r4k.c
index 76f3b9c0a9f0ce60c42e4a9ea8025e1283678bd1..6467d74d2949e98bcc35ab7c368b3c2ea342a6d3 100644
--- a/arch/mips/mm/tlb-r4k.c
+++ b/arch/mips/mm/tlb-r4k.c
@@ -508,6 +508,82 @@ static int __init set_ntlb(char *str)
 
 __setup("ntlb=", set_ntlb);
 
+/*
+ * This is used to set an absolutely safe entryhi value that will not
+ * collide with any existing TLB entries as well as other UNIQUE_ENTRYHI
+ * values.
+ */
+static unsigned long r4k_safe_entryhi(void)
+{
+	int entry = current_cpu_data.tlbsize;
+	int old_index;
+
+	old_index = read_c0_index();
+	while (entry >= 0) {
+		int idx;
+		unsigned long entryhi = UNIQUE_ENTRYHI(entry);
+
+		write_c0_entryhi(entryhi);
+		mtc0_tlbw_hazard();
+		tlb_probe();
+		tlb_probe_hazard();
+		idx = read_c0_index();
+		if (idx < 0) {
+			/* Unused value found */
+			write_c0_index(old_index);
+			mtc0_tlbw_hazard();
+			return entryhi;
+		}
+		entry++;
+	}
+
+	panic("No safe TLB EntryHi value found");
+	return 0;
+}
+
+/*
+ * Initialize all TLB entries with unique values.
+ */
+static void r4k_tlb_uniquify(void)
+{
+	int entry;
+
+	entry = num_wired_entries();
+
+	htw_stop();
+	write_c0_entrylo0(0);
+	write_c0_entrylo1(0);
+	while (entry < current_cpu_data.tlbsize) {
+		unsigned long entryhi;
+		int collision_idx;
+
+		entryhi = UNIQUE_ENTRYHI(entry);
+		write_c0_entryhi(entryhi);
+		mtc0_tlbw_hazard();
+		tlb_probe();
+		tlb_probe_hazard();
+
+		/* Check for possible collision */
+		collision_idx = read_c0_index();
+		if (collision_idx >= 0 && collision_idx != entry) {
+			/* Override collision entry with a safe value */
+			r4k_safe_entryhi();
+			mtc0_tlbw_hazard();
+			tlb_write_indexed();
+			tlbw_use_hazard();
+			/* Recover correputed entryhi */
+			write_c0_entryhi(entryhi);
+		}
+
+		write_c0_index(entry);
+		mtc0_tlbw_hazard();
+		tlb_write_indexed();
+		entry++;
+	}
+	tlbw_use_hazard();
+	htw_start();
+}
+
 /*
  * Configure TLB (for init or after a CPU has been powered off).
  */
@@ -547,7 +623,7 @@ static void r4k_tlb_configure(void)
 	temp_tlb_entry = current_cpu_data.tlbsize - 1;
 
 	/* From this point on the ARC firmware is dead.	 */
-	local_flush_tlb_all();
+	r4k_tlb_uniquify();
 
 	/* Did I tell you that ARC SUCKS?  */
 }

---
base-commit: 911483b25612c8bc32a706ba940738cc43299496
change-id: 20250605-tlb-fix-578bac7be546

Best regards,
-- 
Jiaxun Yang <jiaxun.yang@flygoat.com>


^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2025-06-07 10:37 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2025-06-05 10:02 [PATCH] MIPS: mm: tlb-r4k: Uniquify TLB entries on init Jiaxun Yang
2025-06-06 13:30 ` Jiaxun Yang
2025-06-07  2:48 ` Maciej W. Rozycki
2025-06-07 10:36   ` Jiaxun Yang

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®