[PATCH v2] platform: generic: spacemit: add K1
Troy Mitchell
troy.mitchell at linux.spacemit.com
Sun Sep 21 20:56:08 PDT 2025
Hi Xing W, Thanks for you reviewing.
> > +static void spacemit_k1_pre_init(void)
> > +{
> > + unsigned int hartid, clusterid, cluster_enabled = 0;
> > + unsigned int cur_hartid = current_hartid();
> > + struct sbi_scratch *scratch;
> > + int i;
> > +
> > + scratch = sbi_hartid_to_scratch(cur_hartid);
>
> s/sbi_hartid_to_scratch(cur_hartid)/sbi_scratch_thishart_ptr()/
>
> sbi_hartid_to_scratch can not access before sbi_scratch_init.
Uh, I have double checked the sbi source code,
and I think I can call sbi_hartid_to_scratch() here.
in lib/sbi/sbi_init.c +281:
```
static void __noreturn init_coldboot(struct sbi_scratch *scratch, u32 hartid)
{
int rc;
unsigned long *count;
const struct sbi_platform *plat = sbi_platform_ptr(scratch);
/* Note: This has to be first thing in coldboot init sequence */
rc = sbi_scratch_init(scratch);
if (rc)
sbi_hart_hang();
...
rc = sbi_platform_early_init(plat, true);
if (rc)
sbi_hart_hang();
...
}
```
and k1_pre_init() is called by k1_early_init() after
sbi_scratch_init().
If I'm missing something, please let me know.
But I have checked the API what you mentioned.
That's a right API and I'll use it in the next version.
But I really wanna know if sbi_hartid_to_scratch() can be called here.
- Troy
>
> Regards,
> Xiang W
>
> > +
> > + writel(scratch->warmboot_addr, (unsigned int *)C0_RVBADDR_LO_ADDR);
> > + writel(scratch->warmboot_addr >> 32, (unsigned int *)C0_RVBADDR_HI_ADDR);
> > +
> > + writel(scratch->warmboot_addr, (unsigned int *)C1_RVBADDR_LO_ADDR);
> > + writel(scratch->warmboot_addr >> 32, (unsigned int *)C1_RVBADDR_HI_ADDR);
> > +
> > + for (i = 0; i < platform.hart_count; i++) {
> > + hartid = platform.hart_index2id[i];
> > + clusterid = CPU_TO_CLUSTER(hartid);
> > +
> > + if (!(cluster_enabled & (1 << clusterid))) {
> > + cluster_enabled |= 1 << clusterid;
> > + cci_enable_snoop_dvm_reqs(clusterid);
> > + }
> > + }
> > +}
> > +
> > +/* Start (or power-up) the given hart */
> > +static int spacemit_hart_start(unsigned int hartid, unsigned long saddr)
> > +{
> > + spacemit_wakeup_cpu(hartid);
> > +
> > + return 0;
> > +}
> > +
> > +/*
> > + * Stop (or power-down) the current hart from running. This call
> > + * doesn't expect to return if success.
> > + */
> > +static int spacemit_hart_stop(void)
> > +{
> > + csr_write(CSR_STIMECMP, GENMASK_ULL(63, 0));
> > + csr_clear(CSR_MIE, MIP_SSIP | MIP_MSIP | MIP_STIP | MIP_MTIP | MIP_SEIP | MIP_MEIP);
> > +
> > + /* disable data preftch */
> > + csr_clear(CSR_MSETUP, MSETUP_PFE);
> > + asm volatile ("fence iorw, iorw");
> > +
> > + /* flush local dcache */
> > + csr_write(CSR_MRAOP, MRAOP_ICACHE_INVALID);
> > + asm volatile ("fence iorw, iorw");
> > +
> > + /* disable dcache */
> > + csr_clear(CSR_MSETUP, MSETUP_DE);
> > + asm volatile ("fence iorw, iorw");
> > +
> > + /*
> > + * Core4-7 do not have dedicated bits in ML2SETUP;
> > + * instead, they reuse the same bits as core0-3.
> > + *
> > + * Therefore, use modulo with PLATFORM_MAX_CPUS_PER_CLUSTER
> > + * to select the proper bit.
> > + */
> > + csr_clear(CSR_ML2SETUP, 1 << (current_hartid() % PLATFORM_MAX_CPUS_PER_CLUSTER));
> > + asm volatile ("fence iorw, iorw");
> > +
> > + spacemit_assert_cpu();
> > +
> > + wfi();
> > +
> > + return SBI_ENOTSUPP;
> > +}
> > +
> > +static const struct sbi_hsm_device spacemit_hsm_ops = {
> > + .name = "spacemit-hsm",
> > + .hart_start = spacemit_hart_start,
> > + .hart_stop = spacemit_hart_stop,
> > +};
> > +
> > +/*
> > + * Platform early initialization.
> > + */
> > +static int spacemit_k1_early_init(bool cold_boot)
> > +{
> > + int rc;
> > +
> > + rc = generic_early_init(cold_boot);
> > + if (rc)
> > + return rc;
> > +
> > + csr_set(CSR_MSETUP, MSETUP_DE | MSETUP_IE | MSETUP_BPE |
> > + MSETUP_PFE | MSETUP_MME | MSETUP_ECCE);
> > +
> > + if (cold_boot)
> > + spacemit_k1_pre_init();
> > + else
> > + spacemit_deassert_cpu();
> > +
> > + return 0;
> > +}
> > +
> > +static int spacemit_k1_final_init(bool cold_boot)
> > +{
> > + if (cold_boot)
> > + sbi_hsm_set_device(&spacemit_hsm_ops);
> > +
> > + return generic_final_init(cold_boot);
> > +}
> > +
> > +static bool spacemit_cold_boot_allowed(u32 hartid)
> > +{
> > + csr_set(CSR_ML2SETUP, 1 << (hartid % PLATFORM_MAX_CPUS_PER_CLUSTER));
> > +
> > + return !hartid;
> > +}
> > +
> > +static int spacemit_k1_platform_init(const void *fdt, int nodeoff,
> > + const struct fdt_match *match)
> > +{
> > + generic_platform_ops.early_init = spacemit_k1_early_init;
> > + generic_platform_ops.final_init = spacemit_k1_final_init;
> > + generic_platform_ops.cold_boot_allowed = spacemit_cold_boot_allowed;
> > +
> > + return 0;
> > +}
> > +
> > +static const struct fdt_match spacemit_k1_match[] = {
> > + { .compatible = "spacemit,k1" },
> > + { /* sentinel */ }
> > +};
> > +
> > +const struct fdt_driver spacemit_k1 = {
> > + .match_table = spacemit_k1_match,
> > + .init = spacemit_k1_platform_init,
> > +};
> > diff --git a/platform/generic/spacemit/objects.mk b/platform/generic/spacemit/objects.mk
> > new file mode 100644
> > index 0000000000000000000000000000000000000000..4bf973aab1ba749b59cfdc14a572226d54c3ff15
> > --- /dev/null
> > +++ b/platform/generic/spacemit/objects.mk
> > @@ -0,0 +1,7 @@
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause
> > +#
> > +# Copyright (c) 2025 SpacemiT
> > +
> > +carray-platform_override_modules-$(CONFIG_PLATFORM_SPACEMIT_K1) += spacemit_k1
> > +platform-objs-$(CONFIG_PLATFORM_SPACEMIT_K1) += spacemit/k1.o
> >
> > ---
> > base-commit: 153cdeea5350837c1206a2d2b6189fd0ba06d1f2
> > change-id: 20250911-smt-k1-8-cores-8985c5f40c5f
> >
> > Best regards,
> > --
> > Troy Mitchell <troy.mitchell at linux.spacemit.com>
> >
>
>
More information about the opensbi
mailing list