summaryrefslogtreecommitdiff
path: root/lib/sbi/sbi_init.c
diff options
context:
space:
mode:
authorAnup Patel <anup.patel@wdc.com>2020-09-09 06:49:09 +0300
committerAnup Patel <anup@brainfault.org>2020-09-16 06:35:29 +0300
commit172fa1601c7faaa01c547e8c498f5bdefd52d7cb (patch)
treeabd488410a942da16c3c06440bb3c91628431d4a /lib/sbi/sbi_init.c
parent9f935a4a4372657e43b25fe2f4022fdeb3ca2387 (diff)
downloadopensbi-172fa1601c7faaa01c547e8c498f5bdefd52d7cb.tar.xz
lib: sbi: Ensure coldboot HART supports next privilege mode
The coldboot HART jumps to the next booting stage at the end of init_coldboot() so it is absolutely necessary for coldboot HART to support the privilege mode expected by the next booting stage. We extend the coldboot HART selection in sbi_init() to ensure that the selected coldboot HART always supports privilege mode specified in scratch space (i.e. scratch->next_mode). This will further help us allow E-core (without MMU) on SiFive Unleashed and PolarFire ICICLE boards to proceed further and wait in HSM STOPPED state. Signed-off-by: Anup Patel <anup.patel@wdc.com> Reviewed-by: Atish Patra <atish.patra@wdc.com>
Diffstat (limited to 'lib/sbi/sbi_init.c')
-rw-r--r--lib/sbi/sbi_init.c29
1 files changed, 28 insertions, 1 deletions
diff --git a/lib/sbi/sbi_init.c b/lib/sbi/sbi_init.c
index e1a1d96..65d81ba 100644
--- a/lib/sbi/sbi_init.c
+++ b/lib/sbi/sbi_init.c
@@ -295,6 +295,7 @@ static atomic_t coldboot_lottery = ATOMIC_INITIALIZER(0);
*/
void __noreturn sbi_init(struct sbi_scratch *scratch)
{
+ bool next_mode_supported = FALSE;
bool coldboot = FALSE;
u32 hartid = current_hartid();
const struct sbi_platform *plat = sbi_platform_ptr(scratch);
@@ -303,7 +304,33 @@ void __noreturn sbi_init(struct sbi_scratch *scratch)
sbi_platform_hart_invalid(plat, hartid))
sbi_hart_hang();
- if (atomic_xchg(&coldboot_lottery, 1) == 0)
+ switch (scratch->next_mode) {
+ case PRV_M:
+ next_mode_supported = TRUE;
+ break;
+ case PRV_S:
+ if (misa_extension('S'))
+ next_mode_supported = TRUE;
+ break;
+ case PRV_U:
+ if (misa_extension('U'))
+ next_mode_supported = TRUE;
+ break;
+ default:
+ sbi_hart_hang();
+ }
+
+ /*
+ * Only the HART supporting privilege mode specified in the
+ * scratch->next_mode should be allowed to become the coldboot
+ * HART because the coldboot HART will be directly jumping to
+ * the next booting stage.
+ *
+ * We use a lottery mechanism to select coldboot HART among
+ * HARTs which satisfy above condition.
+ */
+
+ if (next_mode_supported && atomic_xchg(&coldboot_lottery, 1) == 0)
coldboot = TRUE;
if (coldboot)