opensbi: weekly rls 2024.07.20
-0aa741, support cv181x/cv180x suspend to ram. Change-Id: I64dcb0ff942aa7238a88ef3bd1da2c67f5d089b4
This commit is contained in:
committed by
carbon
parent
4df417855c
commit
70b3113ab3
@ -143,6 +143,20 @@ deps-y+=$(libsbi-objs-path-y:.o=.dep)
|
||||
deps-y+=$(libsbiutils-objs-path-y:.o=.dep)
|
||||
deps-y+=$(firmware-objs-path-y:.o=.dep)
|
||||
|
||||
ifeq (,$(wildcard ${PM_SRAM_BIN_PATH}))
|
||||
ifeq (${CHIP_ARCH},CV180X)
|
||||
PM_SRAM_BIN_PATH=${OPENSBI_PATH}/pm_default_cv180x.bin
|
||||
endif
|
||||
ifeq (${CHIP_ARCH},CV181X)
|
||||
PM_SRAM_BIN_PATH=${OPENSBI_PATH}/pm_default_cv181x.bin
|
||||
endif
|
||||
else
|
||||
ifeq ($(filter clean %clean clean%,$(MAKECMDGOALS)),)
|
||||
$(shell touch -c platform\generic\cvitek_riscv.c > /dev/null)
|
||||
endif
|
||||
endif
|
||||
$(info PM_SRAM_BIN_PATH is '${PM_SRAM_BIN_PATH}')
|
||||
|
||||
# Setup platform ABI, ISA and Code Model
|
||||
ifndef PLATFORM_RISCV_ABI
|
||||
ifneq ($(PLATFORM_RISCV_TOOLCHAIN_DEFAULT), 1)
|
||||
@ -212,6 +226,13 @@ CFLAGS += $(GENFLAGS)
|
||||
CFLAGS += $(platform-cflags-y)
|
||||
CFLAGS += -fno-pie -no-pie
|
||||
CFLAGS += $(firmware-cflags-y)
|
||||
CFLAGS += -DPM_SRAM_BIN_PATH=$(PM_SRAM_BIN_PATH)
|
||||
ifeq ($(CHIP_ARCH),CV180X)
|
||||
CFLAGS += -DCONFIG_CV180X
|
||||
endif
|
||||
ifeq (${CHIP_ARCH},CV181X)
|
||||
CFLAGS += -DCONFIG_CV181X
|
||||
endif
|
||||
|
||||
CPPFLAGS += $(GENFLAGS)
|
||||
CPPFLAGS += $(platform-cppflags-y)
|
||||
|
||||
@ -52,6 +52,7 @@ has following details:
|
||||
* **next_mode** - Privilege mode of the next booting stage for this
|
||||
domain. This can be either S-mode or U-mode.
|
||||
* **system_reset_allowed** - Is domain allowed to reset the system?
|
||||
* **system_suspend_allowed** - Is domain allowed to suspend the system?
|
||||
|
||||
The memory regions represented by **regions** in **struct sbi_domain** have
|
||||
following additional constraints to align with RISC-V PMP requirements:
|
||||
@ -91,6 +92,7 @@ following manner:
|
||||
* **next_mode** - Next booting stage mode in coldboot HART scratch space
|
||||
is the next mode for the ROOT domain
|
||||
* **system_reset_allowed** - The ROOT domain is allowed to reset the system
|
||||
* **system_suspend_allowed** - The ROOT domain is allowed to suspend the system
|
||||
|
||||
Domain Effects
|
||||
--------------
|
||||
@ -187,6 +189,8 @@ The DT properties of a domain instance DT node are as follows:
|
||||
stage mode of coldboot HART** is used as default value.
|
||||
* **system-reset-allowed** (Optional) - A boolean flag representing
|
||||
whether the domain instance is allowed to do system reset.
|
||||
* **system-suspend-allowed** (Optional) - A boolean flag representing
|
||||
whether the domain instance is allowed to do system suspend.
|
||||
|
||||
### Assigning HART To Domain Instance
|
||||
|
||||
@ -252,6 +256,7 @@ be done:
|
||||
next-addr = <0x0 0x80100000>;
|
||||
next-mode = <0x0>;
|
||||
system-reset-allowed;
|
||||
system-suspend-allowed;
|
||||
};
|
||||
|
||||
udomain: untrusted-domain {
|
||||
|
||||
@ -78,6 +78,8 @@ struct sbi_domain {
|
||||
unsigned long next_mode;
|
||||
/** Is domain allowed to reset the system */
|
||||
bool system_reset_allowed;
|
||||
/** Is domain allowed to suspend the system */
|
||||
bool system_suspend_allowed;
|
||||
};
|
||||
|
||||
/** The root domain instance */
|
||||
|
||||
@ -39,6 +39,7 @@ extern struct sbi_ecall_extension ecall_ipi;
|
||||
extern struct sbi_ecall_extension ecall_vendor;
|
||||
extern struct sbi_ecall_extension ecall_hsm;
|
||||
extern struct sbi_ecall_extension ecall_srst;
|
||||
extern struct sbi_ecall_extension ecall_susp;
|
||||
|
||||
u16 sbi_ecall_version_major(void);
|
||||
|
||||
|
||||
@ -28,6 +28,7 @@
|
||||
#define SBI_EXT_RFENCE 0x52464E43
|
||||
#define SBI_EXT_HSM 0x48534D
|
||||
#define SBI_EXT_SRST 0x53525354
|
||||
#define SBI_EXT_SUSP 0x53555350
|
||||
|
||||
/* SBI function IDs for BASE extension*/
|
||||
#define SBI_EXT_BASE_GET_SPEC_VERSION 0x0
|
||||
@ -111,6 +112,13 @@
|
||||
#define SBI_ERR_INVALID_ADDRESS -5
|
||||
#define SBI_ERR_ALREADY_AVAILABLE -6
|
||||
|
||||
/* SBI function IDs for SUSP extension */
|
||||
#define SBI_EXT_SUSP_SUSPEND 0x0
|
||||
|
||||
#define SBI_SUSP_SLEEP_TYPE_SUSPEND 0x0
|
||||
#define SBI_SUSP_SLEEP_TYPE_LAST SBI_SUSP_SLEEP_TYPE_SUSPEND
|
||||
#define SBI_SUSP_PLATFORM_SLEEP_START 0x80000000
|
||||
|
||||
#define SBI_LAST_ERR SBI_ERR_ALREADY_AVAILABLE
|
||||
|
||||
/* clang-format on */
|
||||
|
||||
@ -57,9 +57,13 @@ void sbi_hsm_hart_resume_start(struct sbi_scratch *scratch);
|
||||
void sbi_hsm_hart_resume_finish(struct sbi_scratch *scratch);
|
||||
int sbi_hsm_hart_suspend(struct sbi_scratch *scratch, u32 suspend_type,
|
||||
ulong raddr, ulong rmode, ulong priv);
|
||||
int sbi_hsm_hart_change_state(struct sbi_scratch *scratch, long oldstate,
|
||||
long newstate);
|
||||
int __sbi_hsm_hart_get_state(u32 hartid);
|
||||
int sbi_hsm_hart_get_state(const struct sbi_domain *dom, u32 hartid);
|
||||
int sbi_hsm_hart_interruptible_mask(const struct sbi_domain *dom,
|
||||
ulong hbase, ulong *out_hmask);
|
||||
void __sbi_hsm_suspend_non_ret_save(struct sbi_scratch *scratch);
|
||||
void sbi_hsm_prepare_next_jump(struct sbi_scratch *scratch, u32 hartid);
|
||||
|
||||
#endif
|
||||
|
||||
@ -32,4 +32,30 @@ bool sbi_system_reset_supported(u32 reset_type, u32 reset_reason);
|
||||
|
||||
void __noreturn sbi_system_reset(u32 reset_type, u32 reset_reason);
|
||||
|
||||
/** System suspend device */
|
||||
struct sbi_system_suspend_device {
|
||||
/** Name of the system suspend device */
|
||||
char name[32];
|
||||
|
||||
/* Check whether sleep type is supported by the device */
|
||||
int (*system_suspend_check)(u32 sleep_type);
|
||||
|
||||
/**
|
||||
* Suspend the system
|
||||
*
|
||||
* @sleep_type: The sleep type identifier passed to the SBI call.
|
||||
* @mmode_resume_addr:
|
||||
* This is the same as sbi_scratch.warmboot_addr. Some platforms
|
||||
* may not be able to return from system_suspend(), so they will
|
||||
* jump directly to this address instead. Platforms which can
|
||||
* return from system_suspend() may ignore this parameter.
|
||||
*/
|
||||
int (*system_suspend)(u32 sleep_type, unsigned long mmode_resume_addr);
|
||||
};
|
||||
|
||||
const struct sbi_system_suspend_device *sbi_system_suspend_get_device(void);
|
||||
void sbi_system_suspend_set_device(struct sbi_system_suspend_device *dev);
|
||||
bool sbi_system_suspend_supported(u32 sleep_type);
|
||||
int sbi_system_suspend(u32 sleep_type, ulong resume_addr, ulong opaque);
|
||||
|
||||
#endif
|
||||
|
||||
@ -22,6 +22,7 @@ libsbi-objs-y += sbi_ecall_hsm.o
|
||||
libsbi-objs-y += sbi_ecall_legacy.o
|
||||
libsbi-objs-y += sbi_ecall_replace.o
|
||||
libsbi-objs-y += sbi_ecall_vendor.o
|
||||
libsbi-objs-y += sbi_ecall_susp.o
|
||||
libsbi-objs-y += sbi_emulate_csr.o
|
||||
libsbi-objs-y += sbi_fifo.o
|
||||
libsbi-objs-y += sbi_hart.o
|
||||
|
||||
@ -34,6 +34,7 @@ struct sbi_domain root = {
|
||||
.possible_harts = &root_hmask,
|
||||
.regions = root_memregs,
|
||||
.system_reset_allowed = TRUE,
|
||||
.system_suspend_allowed = TRUE,
|
||||
};
|
||||
|
||||
bool sbi_domain_is_assigned_hart(const struct sbi_domain *dom, u32 hartid)
|
||||
@ -383,6 +384,8 @@ void sbi_domain_dump(const struct sbi_domain *dom, const char *suffix)
|
||||
|
||||
sbi_printf("Domain%d SysReset %s: %s\n",
|
||||
dom->index, suffix, (dom->system_reset_allowed) ? "yes" : "no");
|
||||
sbi_printf("Domain%d SysSuspend %s: %s\n",
|
||||
dom->index, suffix, (dom->system_suspend_allowed) ? "yes" : "no");
|
||||
}
|
||||
|
||||
void sbi_domain_dump_all(const char *suffix)
|
||||
|
||||
@ -168,6 +168,9 @@ int sbi_ecall_init(void)
|
||||
if (ret)
|
||||
return ret;
|
||||
ret = sbi_ecall_register_extension(&ecall_vendor);
|
||||
if (ret)
|
||||
return ret;
|
||||
ret = sbi_ecall_register_extension(&ecall_susp);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
|
||||
60
opensbi/lib/sbi/sbi_ecall_susp.c
Normal file
60
opensbi/lib/sbi/sbi_ecall_susp.c
Normal file
@ -0,0 +1,60 @@
|
||||
// SPDX-License-Identifier: BSD-2-Clause
|
||||
#include <sbi/sbi_ecall.h>
|
||||
#include <sbi/sbi_ecall_interface.h>
|
||||
#include <sbi/sbi_error.h>
|
||||
#include <sbi/sbi_trap.h>
|
||||
#include <sbi/sbi_system.h>
|
||||
|
||||
static int sbi_ecall_susp_handler(unsigned long extid, unsigned long funcid,
|
||||
const struct sbi_trap_regs *regs,
|
||||
unsigned long *out_val,
|
||||
struct sbi_trap_info *out_trap)
|
||||
{
|
||||
int ret = SBI_ENOTSUPP;
|
||||
|
||||
if (funcid == SBI_EXT_SUSP_SUSPEND)
|
||||
ret = sbi_system_suspend(regs->a0, regs->a1, regs->a2);
|
||||
|
||||
if (ret >= 0) {
|
||||
*out_val = ret;
|
||||
ret = 0;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static bool susp_available(void)
|
||||
{
|
||||
u32 type;
|
||||
|
||||
/*
|
||||
* At least one suspend type should be supported by the
|
||||
* platform for the SBI SUSP extension to be usable.
|
||||
*/
|
||||
for (type = 0; type <= SBI_SUSP_SLEEP_TYPE_LAST; type++) {
|
||||
if (sbi_system_suspend_supported(type))
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
struct sbi_ecall_extension ecall_susp;
|
||||
|
||||
static int sbi_ecall_susp_register_extensions(unsigned long extid, unsigned long *out_val)
|
||||
{
|
||||
if (!susp_available()) {
|
||||
*out_val = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
*out_val = 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
struct sbi_ecall_extension ecall_susp = {
|
||||
.extid_start = SBI_EXT_SUSP,
|
||||
.extid_end = SBI_EXT_SUSP,
|
||||
.probe = sbi_ecall_susp_register_extensions,
|
||||
.handle = sbi_ecall_susp_handler,
|
||||
};
|
||||
@ -36,8 +36,25 @@ struct sbi_hsm_data {
|
||||
unsigned long saved_mie;
|
||||
unsigned long saved_mip;
|
||||
};
|
||||
#define __sbi_hsm_hart_change_state(hdata, oldstate, newstate) \
|
||||
({ \
|
||||
long state = atomic_cmpxchg(&(hdata)->state, oldstate, newstate); \
|
||||
if (state != (oldstate)) \
|
||||
sbi_printf("%s: ERR: The hart is in invalid state [%lu]\n", \
|
||||
__func__, state); \
|
||||
state == (oldstate); \
|
||||
})
|
||||
|
||||
static inline int __sbi_hsm_hart_get_state(u32 hartid)
|
||||
int sbi_hsm_hart_change_state(struct sbi_scratch *scratch, long oldstate,
|
||||
long newstate)
|
||||
{
|
||||
struct sbi_hsm_data *hdata = sbi_scratch_offset_ptr(scratch,
|
||||
hart_data_offset);
|
||||
|
||||
return __sbi_hsm_hart_change_state(hdata, oldstate, newstate);
|
||||
}
|
||||
|
||||
int __sbi_hsm_hart_get_state(u32 hartid)
|
||||
{
|
||||
struct sbi_hsm_data *hdata;
|
||||
struct sbi_scratch *scratch;
|
||||
@ -322,7 +339,7 @@ static int __sbi_hsm_suspend_ret_default(struct sbi_scratch *scratch)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void __sbi_hsm_suspend_non_ret_save(struct sbi_scratch *scratch)
|
||||
void __sbi_hsm_suspend_non_ret_save(struct sbi_scratch *scratch)
|
||||
{
|
||||
struct sbi_hsm_data *hdata = sbi_scratch_offset_ptr(scratch,
|
||||
hart_data_offset);
|
||||
|
||||
@ -58,6 +58,7 @@ static void sbi_boot_print_general(struct sbi_scratch *scratch)
|
||||
const struct sbi_timer_device *tdev;
|
||||
const struct sbi_console_device *cdev;
|
||||
const struct sbi_system_reset_device *srdev;
|
||||
const struct sbi_system_suspend_device *susp_dev;
|
||||
const struct sbi_platform *plat = sbi_platform_ptr(scratch);
|
||||
|
||||
if (scratch->options & SBI_SCRATCH_NO_BOOT_PRINTS)
|
||||
@ -85,6 +86,9 @@ static void sbi_boot_print_general(struct sbi_scratch *scratch)
|
||||
srdev = sbi_system_reset_get_device();
|
||||
sbi_printf("Platform SysReset Device : %s\n",
|
||||
(srdev) ? srdev->name : "---");
|
||||
susp_dev = sbi_system_suspend_get_device();
|
||||
sbi_printf("Platform Suspend Device : %s\n",
|
||||
(susp_dev) ? susp_dev->name : "---");
|
||||
|
||||
/* Firmware details */
|
||||
sbi_printf("Firmware Base : 0x%lx\n", scratch->fw_start);
|
||||
|
||||
@ -72,3 +72,88 @@ void __noreturn sbi_system_reset(u32 reset_type, u32 reset_reason)
|
||||
/* If platform specific reset did not work then do sbi_exit() */
|
||||
sbi_exit(scratch);
|
||||
}
|
||||
|
||||
static const struct sbi_system_suspend_device *suspend_dev;
|
||||
|
||||
const struct sbi_system_suspend_device *sbi_system_suspend_get_device(void)
|
||||
{
|
||||
return suspend_dev;
|
||||
}
|
||||
|
||||
void sbi_system_suspend_set_device(struct sbi_system_suspend_device *dev)
|
||||
{
|
||||
if (!dev || suspend_dev)
|
||||
return;
|
||||
|
||||
suspend_dev = dev;
|
||||
}
|
||||
|
||||
bool sbi_system_suspend_supported(u32 sleep_type)
|
||||
{
|
||||
return suspend_dev && suspend_dev->system_suspend_check &&
|
||||
suspend_dev->system_suspend_check(sleep_type) == 0;
|
||||
}
|
||||
|
||||
int sbi_system_suspend(u32 sleep_type, ulong resume_addr, ulong opaque)
|
||||
{
|
||||
const struct sbi_domain *dom = sbi_domain_thishart_ptr();
|
||||
struct sbi_scratch *scratch = sbi_scratch_thishart_ptr();
|
||||
void (*jump_warmboot)(void) = (void (*)(void))scratch->warmboot_addr;
|
||||
//unsigned int hartid = current_hartid();
|
||||
unsigned long prev_mode;
|
||||
//unsigned long i, j;
|
||||
int ret;
|
||||
|
||||
if (!dom || !dom->system_suspend_allowed)
|
||||
return SBI_EFAIL;
|
||||
|
||||
if (!suspend_dev || !suspend_dev->system_suspend ||
|
||||
!suspend_dev->system_suspend_check)
|
||||
return SBI_EFAIL;
|
||||
|
||||
ret = suspend_dev->system_suspend_check(sleep_type);
|
||||
if (ret != SBI_OK)
|
||||
return ret;
|
||||
|
||||
prev_mode = (csr_read(CSR_MSTATUS) & MSTATUS_MPP) >> MSTATUS_MPP_SHIFT;
|
||||
if (prev_mode != PRV_S && prev_mode != PRV_U)
|
||||
return SBI_EFAIL;
|
||||
|
||||
//FIX ME: hartindex to hart
|
||||
//sbi_hartmask_for_each_hartindex(j, &dom->assigned_harts) {
|
||||
// //i = sbi_hartindex_to_hartid(j);
|
||||
// if (i == hartid)
|
||||
// continue;
|
||||
// if (__sbi_hsm_hart_get_state(i) != SBI_HSM_STATE_STOPPED)
|
||||
// return SBI_ERR_DENIED;
|
||||
//}
|
||||
|
||||
if (!sbi_domain_check_addr(dom, resume_addr, prev_mode,
|
||||
SBI_DOMAIN_EXECUTE))
|
||||
return SBI_EINVALID_ADDR;
|
||||
|
||||
if (!sbi_hsm_hart_change_state(scratch, SBI_HSM_STATE_STARTED,
|
||||
SBI_HSM_STATE_SUSPENDED))
|
||||
return SBI_EFAIL;
|
||||
|
||||
/* Prepare for resume */
|
||||
scratch->next_mode = prev_mode;
|
||||
scratch->next_addr = resume_addr;
|
||||
scratch->next_arg1 = opaque;
|
||||
|
||||
__sbi_hsm_suspend_non_ret_save(scratch);
|
||||
|
||||
/* Suspend */
|
||||
ret = suspend_dev->system_suspend(sleep_type, scratch->warmboot_addr);
|
||||
if (ret != SBI_OK) {
|
||||
if (!sbi_hsm_hart_change_state(scratch, SBI_HSM_STATE_SUSPENDED,
|
||||
SBI_HSM_STATE_STARTED))
|
||||
sbi_hart_hang();
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* Resume */
|
||||
jump_warmboot();
|
||||
|
||||
__builtin_unreachable();
|
||||
}
|
||||
|
||||
@ -398,6 +398,13 @@ static int __fdt_parse_domain(void *fdt, int domain_offset, void *opaque)
|
||||
else
|
||||
dom->system_reset_allowed = FALSE;
|
||||
|
||||
/* Read "system-suspend-allowed" DT property */
|
||||
if (fdt_get_property(fdt, domain_offset,
|
||||
"system-suspend-allowed", NULL))
|
||||
dom->system_suspend_allowed = TRUE;
|
||||
else
|
||||
dom->system_suspend_allowed = FALSE;
|
||||
|
||||
/* Find /cpus DT node */
|
||||
cpus_offset = fdt_path_offset(fdt, "/cpus");
|
||||
if (cpus_offset < 0)
|
||||
|
||||
107
opensbi/platform/generic/cvitek_riscv.c
Normal file
107
opensbi/platform/generic/cvitek_riscv.c
Normal file
@ -0,0 +1,107 @@
|
||||
/*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*
|
||||
* Copyright (c) 2020 Western Digital Corporation or its affiliates.
|
||||
*
|
||||
* Authors:
|
||||
* Anup Patel <anup.patel@wdc.com>
|
||||
*/
|
||||
|
||||
#include <platform_override.h>
|
||||
#include <sbi_utils/fdt/fdt_helper.h>
|
||||
#include <sbi_utils/fdt/fdt_fixup.h>
|
||||
#include <sbi/sbi_system.h>
|
||||
#include <sbi/sbi_ecall_interface.h>
|
||||
#include <sbi/sbi_string.h>
|
||||
#include <sbi/sbi_types.h>
|
||||
#include <sbi/sbi_error.h>
|
||||
#include <sbi/riscv_asm.h>
|
||||
#include <sbi/riscv_io.h>
|
||||
|
||||
__asm__(".section .rodata\n"
|
||||
".global suspend_sram_entry\n"
|
||||
".global suspend_sram_end\n"
|
||||
".type suspend_sram_entry, @object\n"
|
||||
".type suspend_sram_end, @object\n"
|
||||
".align 4\n"
|
||||
"suspend_sram_entry:\n"
|
||||
".incbin \"" STRINGIFY(PM_SRAM_BIN_PATH) "\"\n"
|
||||
".align 4\n"
|
||||
"suspend_sram_end:\n"
|
||||
".text\n");
|
||||
|
||||
#define RTC_SRAM_FLAG_ADDR 0x05026ff8
|
||||
#ifdef CONFIG_CV180X
|
||||
#define SUSPEND_SRAM_ENTRY 0x3C000000
|
||||
#endif
|
||||
#ifdef CONFIG_CV181X
|
||||
#define SUSPEND_SRAM_ENTRY 0xC030000
|
||||
#endif
|
||||
#define memcpy sbi_memcpy
|
||||
|
||||
static void rtc_latch_pinmux_settings(void)
|
||||
{
|
||||
writel(0x2, (void *)0x50250ac);
|
||||
writel(0x0, (void *)0x5027084);
|
||||
//TODO
|
||||
}
|
||||
|
||||
static void rtc_power_saving_settings_for_suspend(void)
|
||||
{
|
||||
//TODO
|
||||
}
|
||||
|
||||
static int cvitek_sbi_system_suspend_check(u32 sleep_type)
|
||||
{
|
||||
return sleep_type == SBI_SUSP_SLEEP_TYPE_SUSPEND ? 0 : SBI_EINVAL;
|
||||
}
|
||||
|
||||
static int cvitek_sbi_system_suspend(u32 sleep_type,
|
||||
unsigned long mmode_resume_addr)
|
||||
{
|
||||
void (*suspend)(void) = (void *)SUSPEND_SRAM_ENTRY;
|
||||
|
||||
if (sleep_type != SBI_SUSP_SLEEP_TYPE_SUSPEND)
|
||||
return SBI_EINVAL;
|
||||
|
||||
rtc_latch_pinmux_settings();
|
||||
rtc_power_saving_settings_for_suspend();
|
||||
|
||||
/* store warmboot entry for resume*/
|
||||
writel(mmode_resume_addr, (void *)RTC_SRAM_FLAG_ADDR);
|
||||
writel(readl((void *)0x03002000) | 0x10, (void *)0x03002000); //enable TPU clock
|
||||
memcpy((void *)SUSPEND_SRAM_ENTRY, suspend_sram_entry, suspend_sram_end - suspend_sram_entry);
|
||||
|
||||
asm volatile("fence.i" ::: "memory");
|
||||
|
||||
asm volatile("fence rw,rw\n\t");
|
||||
|
||||
suspend();
|
||||
|
||||
wfi();
|
||||
|
||||
return SBI_OK;
|
||||
}
|
||||
|
||||
static struct sbi_system_suspend_device cvitek_sbi_suspend_device = {
|
||||
.name = "cvi-suspend",
|
||||
.system_suspend_check = cvitek_sbi_system_suspend_check,
|
||||
.system_suspend = cvitek_sbi_system_suspend,
|
||||
};
|
||||
|
||||
static int cvitek_riscv_early_init(bool cold_boot, const struct fdt_match *match)
|
||||
{
|
||||
sbi_system_suspend_set_device(&cvitek_sbi_suspend_device);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const struct fdt_match cvitek_riscv_match[] = {
|
||||
{ .compatible = "cvitek,cv180x" },
|
||||
{ .compatible = "cvitek,cv181x" }
|
||||
};
|
||||
|
||||
const struct platform_override cvitek_riscv = {
|
||||
.match_table = cvitek_riscv_match,
|
||||
.early_init = cvitek_riscv_early_init,
|
||||
};
|
||||
@ -12,6 +12,11 @@
|
||||
|
||||
#include <sbi/sbi_types.h>
|
||||
|
||||
extern const struct platform_override sifive_fu540;
|
||||
extern const struct platform_override cvitek_riscv;
|
||||
extern u8 suspend_sram_entry[];
|
||||
extern u8 suspend_sram_end[];
|
||||
|
||||
struct platform_override {
|
||||
const struct fdt_match *match_table;
|
||||
u64 (*features)(const struct fdt_match *match);
|
||||
|
||||
@ -9,3 +9,4 @@
|
||||
|
||||
platform-objs-y += platform.o
|
||||
platform-objs-y += sifive_fu540.o
|
||||
platform-objs-y += cvitek_riscv.o
|
||||
|
||||
@ -22,10 +22,9 @@
|
||||
#include <sbi_utils/ipi/fdt_ipi.h>
|
||||
#include <sbi_utils/reset/fdt_reset.h>
|
||||
|
||||
extern const struct platform_override sifive_fu540;
|
||||
|
||||
static const struct platform_override *special_platforms[] = {
|
||||
&sifive_fu540,
|
||||
&cvitek_riscv,
|
||||
};
|
||||
|
||||
static const struct platform_override *generic_plat = NULL;
|
||||
|
||||
BIN
opensbi/pm_default_cv180x.bin
Executable file
BIN
opensbi/pm_default_cv180x.bin
Executable file
Binary file not shown.
BIN
opensbi/pm_default_cv181x.bin
Executable file
BIN
opensbi/pm_default_cv181x.bin
Executable file
Binary file not shown.
Reference in New Issue
Block a user