Skip to contentSkip to conversation

generic: mips: support harts to boot from mips_warm_boot

PATCH Superseded Chao-ying Fu 3 participants 5 messages Jul 11, 2025 – Jul 22, 2025

v1 of 3 Superseded Latest is v3 →

lore
Share & tools
lore
#0 lore raw

PATCH 1/1 generic: mips: support harts to boot from mips_warm_boot

We program reset base for harts (other than hart 0) to boot at mips_warm_boot that jumps to _start_warm. This helps to skip some code sequence to speed up.

---
 platform/generic/mips/p8700.c | 19 +++++++++++++++++++
 1 file changed, 19 insertions(+)
platform/generic/mips/p8700.c +19 -0
index 888a45c..687912a 100644
@@ -140,6 +140,22 @@ static void power_up_other_cluster(u32 hartid)
 }
 #endif
 
+static void __attribute__((naked,no_instrument_function,aligned(4096)))
+mips_warm_boot(void)
+{
+  __asm__ __volatile__(
+	"	j	1f\n"
+	"	.align	2\n"
+	"	j	1f\n"
+	"	.align	2\n"
+	"	j	1f\n"
+	"	.align	2\n"
+	"	j	1f\n"
+	"1:	lla	t0, _start_warm\n"
+	"	jr	t0\n"
+	);
+}
+
 static int mips_hart_start(u32 hartid, ulong saddr)
 {
 	unsigned int stat;
@@ -150,6 +166,9 @@ static int mips_hart_start(u32 hartid, ulong saddr)
 	if (hartid == 0)
 		return SBI_ENOTSUPP;
 
+	/* Change reset base to mips_warm_boot */
+	write_gcr_co_reset_base(hartid, (unsigned long)mips_warm_boot, local_p);
+
 	if (cpu_hart(hartid) == 0) {
 		/* Ensure its coherency is disabled */
 		write_gcr_co_coherence(hartid, 0, local_p);
Signature · 7 lines
2.47.1


-- 
opensbi mailing list
[email protected]
http://lists.infradead.org/mailman/listinfo/opensbi
#1 lore raw
Quoted 23 lines · Chao-ying Fu

We program reset base for harts (other than hart 0) to boot at mips_warm_boot that jumps to _start_warm. This helps to skip some code sequence to speed up.

---
platform/generic/mips/p8700.c | 19 +++++++++++++++++++

1 file changed, 19 insertions(+)
platform/generic/mips/p8700.c +5 -0
index 888a45c..687912a 100644
@@ -140,6 +140,22 @@ static void power_up_other_cluster(u32 hartid)
 }
 #endif
 
+static void __attribute__((naked,no_instrument_function,aligned(4096)))
+mips_warm_boot(void)
+{
+  __asm__ __volatile__(
+ " j 1f\n"

platform/generic/mips/p8700.c static void power_up_other_cluster(u32 hartid) · line 157

Quoted 10 lines
platform/generic/mips/p8700.c +10 -0
+ " .align 2\n"
+ " j 1f\n"
+ " .align 2\n"
+ " j 1f\n"
+ " .align 2\n"
+ " j 1f\n"
+ "1: lla t0, _start_warm\n"
+ " jr t0\n"
+ );
+}

What is the point of writing this as a C function if it’s going to be entirely assembly? Just write an assembly function?

Jess

Signature · 3 lines
opensbi mailing list
[email protected]
http://lists.infradead.org/mailman/listinfo/opensbi
#2 lore raw
Quoted 30 lines · Jessica Clarke
Quoted 28 lines · Chao-ying Fu

We program reset base for harts (other than hart 0) to boot at mips_warm_boot that jumps to _start_warm. This helps to skip some code sequence to speed up.

---
platform/generic/mips/p8700.c | 19 +++++++++++++++++++

1 file changed, 19 insertions(+)
platform/generic/mips/p8700.c +10 -0
index 888a45c..687912a 100644
@@ -140,6 +140,22 @@ static void power_up_other_cluster(u32 hartid)
 }
 #endif
 
+static void __attribute__((naked,no_instrument_function,aligned(4096)))
+mips_warm_boot(void)
+{
+  __asm__ __volatile__(
+ " j 1f\n"
+ " .align 2\n"
+ " j 1f\n"
+ " .align 2\n"
+ " j 1f\n"
+ " .align 2\n"
Quoted 8 lines

platform/generic/mips/p8700.c static void power_up_other_cluster(u32 hartid) · line 157

Quoted 5 lines
platform/generic/mips/p8700.c +5 -0
+ " j 1f\n"
+ "1: lla t0, _start_warm\n"
+ " jr t0\n"
+ );
+}

What is the point of writing this as a C function if it’s going to be entirely assembly? Just write an assembly function?

My intention is to have a minimum change, as there is only one file
modified in the patch.
Either writing assembly code or writing C code for mips_warm_boot is fine or equivalent.
To have assembly code, we will need to modify Makefile and create a new assembly file in the patch.

Thanks a lot!

Regards,
Chao-ying

Signature · 3 lines
opensbi mailing list
[email protected]
http://lists.infradead.org/mailman/listinfo/opensbi
#3 lore raw
In reply to Chao-ying Fu
Quoted 20 lines · Chao-ying Fu

We program reset base for harts (other than hart 0) to boot at mips_warm_boot that jumps to _start_warm. This helps to skip some code sequence to speed up.

---
 platform/generic/mips/p8700.c | 19 +++++++++++++++++++
 1 file changed, 19 insertions(+)
platform/generic/mips/p8700.c +3 -0
index 888a45c..687912a 100644
@@ -140,6 +140,22 @@ static void power_up_other_cluster(u32 hartid)
 }
 #endif
 
+static void __attribute__((naked,no_instrument_function,aligned(4096)))
+mips_warm_boot(void)
+{

platform/generic/mips/p8700.c static void power_up_other_cluster(u32 hartid) · line 155

Quoted 10 lines
platform/generic/mips/p8700.c +10 -0
+  __asm__ __volatile__(
+	"	j	1f\n"
+	"	.align	2\n"
+	"	j	1f\n"
+	"	.align	2\n"
+	"	j	1f\n"
+	"	.align	2\n"
+	"	j	1f\n"
+	"1:	lla	t0, _start_warm\n"
+	"	jr	t0\n"

The double/indirect jump is not necessary. jal (j) range is +/- 1 MiB, which is much larger than the OpenSBI firmware size. So each entry point can jump to _start_warm directly.

Regards,
Samuel

Quoted 16 lines
platform/generic/mips/p8700.c +6 -0
+	);
+}
+
 static int mips_hart_start(u32 hartid, ulong saddr)
 {
 	unsigned int stat;
@@ -150,6 +166,9 @@ static int mips_hart_start(u32 hartid, ulong saddr)
 	if (hartid == 0)
 		return SBI_ENOTSUPP;
 
+	/* Change reset base to mips_warm_boot */
+	write_gcr_co_reset_base(hartid, (unsigned long)mips_warm_boot, local_p);
+
 	if (cpu_hart(hartid) == 0) {
 		/* Ensure its coherency is disabled */
 		write_gcr_co_coherence(hartid, 0, local_p);
Signature · 3 lines
opensbi mailing list
[email protected]
http://lists.infradead.org/mailman/listinfo/opensbi
#4 lore raw
Quoted 37 lines · Samuel Holland
Quoted 20 lines · Chao-ying Fu

We program reset base for harts (other than hart 0) to boot at mips_warm_boot that jumps to _start_warm. This helps to skip some code sequence to speed up.

---
 platform/generic/mips/p8700.c | 19 +++++++++++++++++++
 1 file changed, 19 insertions(+)
platform/generic/mips/p8700.c +3 -0
index 888a45c..687912a 100644
@@ -140,6 +140,22 @@ static void power_up_other_cluster(u32 hartid)
 }
 #endif
 
+static void __attribute__((naked,no_instrument_function,aligned(4096)))
+mips_warm_boot(void)
+{

platform/generic/mips/p8700.c static void power_up_other_cluster(u32 hartid) · line 155

Quoted 10 lines
platform/generic/mips/p8700.c +10 -0
+  __asm__ __volatile__(
+     "       j       1f\n"
+     "       .align  2\n"
+     "       j       1f\n"
+     "       .align  2\n"
+     "       j       1f\n"
+     "       .align  2\n"
+     "       j       1f\n"
+     "1:     lla     t0, _start_warm\n"
+     "       jr      t0\n"

The double/indirect jump is not necessary. jal (j) range is +/- 1 MiB, which is much larger than the OpenSBI firmware size. So each entry point can jump to _start_warm directly.

Quoted 2 lines

Regards,
Samuel

Yes, we can use only one jump instruction to _start_warm for each
entry point, as you pointed out.
I will send out a new patch.

Thanks a lot!

Regards,
Chao-ying

Quoted 18 lines
Quoted 17 lines
platform/generic/mips/p8700.c +6 -0
+     );
+}
+
 static int mips_hart_start(u32 hartid, ulong saddr)
 {
      unsigned int stat;
@@ -150,6 +166,9 @@ static int mips_hart_start(u32 hartid, ulong saddr)
      if (hartid == 0)
              return SBI_ENOTSUPP;
 
+     /* Change reset base to mips_warm_boot */
+     write_gcr_co_reset_base(hartid, (unsigned long)mips_warm_boot, local_p);
+
      if (cpu_hart(hartid) == 0) {
              /* Ensure its coherency is disabled */
              write_gcr_co_coherence(hartid, 0, local_p);
Signature · 3 lines
opensbi mailing list
[email protected]
http://lists.infradead.org/mailman/listinfo/opensbi