svn commit: r360553 - head/sys/riscv/riscv
Mitchell Horne
mhorne at FreeBSD.org
Fri May 1 21:58:20 UTC 2020
Author: mhorne
Date: Fri May 1 21:58:19 2020
New Revision: 360553
URL: https://svnweb.freebsd.org/changeset/base/360553
Log:
Use the HSM SBI extension to start APs
The addition of the HSM SBI extension to OpenSBI introduces a new
breaking change: secondary harts will remain parked in the firmware,
until they are brought up explicitly via sbi_hsm_hart_start(). Add
the call to do this, sending the secondary harts to mpentry.
If the HSM extension is not present, secondary harts are assumed to be
released by the firmware, as is the case for OpenSBI =< v0.6 and BBL.
In the case that the HSM call fails we exclude the CPU, notify the
user, and allow the system to proceed with booting.
Reviewed by: markj (older version)
Differential Revision: https://reviews.freebsd.org/D24497
Modified:
head/sys/riscv/riscv/mp_machdep.c
Modified: head/sys/riscv/riscv/mp_machdep.c
==============================================================================
--- head/sys/riscv/riscv/mp_machdep.c Fri May 1 21:55:51 2020 (r360552)
+++ head/sys/riscv/riscv/mp_machdep.c Fri May 1 21:58:19 2020 (r360553)
@@ -97,6 +97,7 @@ static uint32_t cpu_reg[MAXCPU][2];
#endif
static device_t cpu_list[MAXCPU];
+void mpentry(u_long hartid);
void init_secondary(uint64_t);
static struct mtx ap_boot_mtx;
@@ -297,7 +298,7 @@ smp_after_idle_runnable(void *arg __unused)
struct pcpu *pc;
int cpu;
- for (cpu = 1; cpu < mp_ncpus; cpu++) {
+ for (cpu = 1; cpu <= mp_maxid; cpu++) {
if (bootstacks[cpu] != NULL) {
pc = pcpu_find(cpu);
while (atomic_load_ptr(&pc->pc_curpcb) == NULL)
@@ -399,9 +400,11 @@ static boolean_t
cpu_init_fdt(u_int id, phandle_t node, u_int addr_size, pcell_t *reg)
{
struct pcpu *pcpup;
+ vm_paddr_t start_addr;
uint64_t hart;
u_int cpuid;
int naps;
+ int error;
/* Check if this hart supports MMU. */
if (OF_getproplen(node, "mmu-type") < 0)
@@ -440,6 +443,23 @@ cpu_init_fdt(u_int id, phandle_t node, u_int addr_size
/* Check if we are able to start this cpu */
if (cpuid > mp_maxid)
return (0);
+
+ /*
+ * Depending on the SBI implementation, APs are waiting either in
+ * locore.S or to be activated explicitly, via SBI call.
+ */
+ if (sbi_probe_extension(SBI_EXT_ID_HSM) != 0) {
+ start_addr = pmap_kextract((vm_offset_t)mpentry);
+ error = sbi_hsm_hart_start(hart, start_addr, 0);
+ if (error != 0) {
+ mp_ncpus--;
+
+ /* Send a warning to the user and continue. */
+ printf("AP %u (hart %lu) failed to start, error %d\n",
+ cpuid, hart, error);
+ return (0);
+ }
+ }
pcpup = &__pcpu[cpuid];
pcpu_init(pcpup, cpuid, sizeof(struct pcpu));
More information about the svn-src-all
mailing list