mirror of
https://github.com/AsahiLinux/u-boot
synced 2024-11-10 15:14:43 +00:00
riscv: cache: Implement i/dcache [status, enable, disable]
AndeStar RISC-V(V5) provide mcache_ctl register which can configure I/D cache as enabled or disabled. This CSR will be encapsulated by CONFIG_RISCV_NDS. If you want to configure cache on AndeStar V5 AE350 platform. YOu can enable [*] AndeStar V5 ISA support by make menuconfig. This approach also provide the expansion when the vender specific features are going to join in. Signed-off-by: Rick Chen <rick@andestech.com> Cc: Greentime Hu <greentime@andestech.com>
This commit is contained in:
parent
bae2d72507
commit
52923c6db7
9 changed files with 148 additions and 12 deletions
|
@ -16,9 +16,15 @@ config TARGET_QEMU_VIRT
|
|||
|
||||
endchoice
|
||||
|
||||
# board-specific options below
|
||||
source "board/AndesTech/ax25-ae350/Kconfig"
|
||||
source "board/emulation/qemu-riscv/Kconfig"
|
||||
|
||||
# platform-specific options below
|
||||
source "arch/riscv/cpu/ax25/Kconfig"
|
||||
|
||||
# architecture-specific options below
|
||||
|
||||
choice
|
||||
prompt "Base ISA"
|
||||
default ARCH_RV32I
|
||||
|
|
7
arch/riscv/cpu/ax25/Kconfig
Normal file
7
arch/riscv/cpu/ax25/Kconfig
Normal file
|
@ -0,0 +1,7 @@
|
|||
config RISCV_NDS
|
||||
bool "AndeStar V5 ISA support"
|
||||
default n
|
||||
help
|
||||
Say Y here if you plan to run U-Boot on AndeStar v5
|
||||
platforms and use some specific features which are
|
||||
provided by Andes Technology AndeStar V5 Families.
|
|
@ -4,3 +4,4 @@
|
|||
# Rick Chen, Andes Technology Corporation <rick@andestech.com>
|
||||
|
||||
obj-y := cpu.o
|
||||
obj-y += cache.o
|
||||
|
|
95
arch/riscv/cpu/ax25/cache.c
Normal file
95
arch/riscv/cpu/ax25/cache.c
Normal file
|
@ -0,0 +1,95 @@
|
|||
// SPDX-License-Identifier: GPL-2.0+
|
||||
/*
|
||||
* Copyright (C) 2017 Andes Technology Corporation
|
||||
* Rick Chen, Andes Technology Corporation <rick@andestech.com>
|
||||
*/
|
||||
|
||||
#include <common.h>
|
||||
|
||||
void icache_enable(void)
|
||||
{
|
||||
#ifndef CONFIG_SYS_ICACHE_OFF
|
||||
#ifdef CONFIG_RISCV_NDS
|
||||
asm volatile (
|
||||
"csrr t1, mcache_ctl\n\t"
|
||||
"ori t0, t1, 0x1\n\t"
|
||||
"csrw mcache_ctl, t0\n\t"
|
||||
);
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
|
||||
void icache_disable(void)
|
||||
{
|
||||
#ifndef CONFIG_SYS_ICACHE_OFF
|
||||
#ifdef CONFIG_RISCV_NDS
|
||||
asm volatile (
|
||||
"fence.i\n\t"
|
||||
"csrr t1, mcache_ctl\n\t"
|
||||
"andi t0, t1, ~0x1\n\t"
|
||||
"csrw mcache_ctl, t0\n\t"
|
||||
);
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
|
||||
void dcache_enable(void)
|
||||
{
|
||||
#ifndef CONFIG_SYS_DCACHE_OFF
|
||||
#ifdef CONFIG_RISCV_NDS
|
||||
asm volatile (
|
||||
"csrr t1, mcache_ctl\n\t"
|
||||
"ori t0, t1, 0x2\n\t"
|
||||
"csrw mcache_ctl, t0\n\t"
|
||||
);
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
|
||||
void dcache_disable(void)
|
||||
{
|
||||
#ifndef CONFIG_SYS_DCACHE_OFF
|
||||
#ifdef CONFIG_RISCV_NDS
|
||||
asm volatile (
|
||||
"fence\n\t"
|
||||
"csrr t1, mcache_ctl\n\t"
|
||||
"andi t0, t1, ~0x2\n\t"
|
||||
"csrw mcache_ctl, t0\n\t"
|
||||
);
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
|
||||
int icache_status(void)
|
||||
{
|
||||
int ret = 0;
|
||||
|
||||
#ifdef CONFIG_RISCV_NDS
|
||||
asm volatile (
|
||||
"csrr t1, mcache_ctl\n\t"
|
||||
"andi %0, t1, 0x01\n\t"
|
||||
: "=r" (ret)
|
||||
:
|
||||
: "memory"
|
||||
);
|
||||
#endif
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
int dcache_status(void)
|
||||
{
|
||||
int ret = 0;
|
||||
|
||||
#ifdef CONFIG_RISCV_NDS
|
||||
asm volatile (
|
||||
"csrr t1, mcache_ctl\n\t"
|
||||
"andi %0, t1, 0x02\n\t"
|
||||
: "=r" (ret)
|
||||
:
|
||||
: "memory"
|
||||
);
|
||||
#endif
|
||||
|
||||
return ret;
|
||||
}
|
|
@ -6,6 +6,7 @@
|
|||
|
||||
/* CPU specific code */
|
||||
#include <common.h>
|
||||
#include <asm/cache.h>
|
||||
|
||||
/*
|
||||
* cleanup_before_linux() is called just before we call linux
|
||||
|
@ -18,6 +19,9 @@ int cleanup_before_linux(void)
|
|||
disable_interrupts();
|
||||
|
||||
/* turn off I/D-cache */
|
||||
cache_flush();
|
||||
icache_disable();
|
||||
dcache_disable();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -15,7 +15,7 @@ int cleanup_before_linux(void)
|
|||
{
|
||||
disable_interrupts();
|
||||
|
||||
/* turn off I/D-cache */
|
||||
cache_flush();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -46,6 +46,10 @@ _start:
|
|||
/* mask all interrupts */
|
||||
csrw mie, zero
|
||||
|
||||
/* Enable cache */
|
||||
jal icache_enable
|
||||
jal dcache_enable
|
||||
|
||||
/*
|
||||
* Set stackpointer in internal/ex RAM to call board_init_f
|
||||
*/
|
||||
|
@ -181,6 +185,8 @@ clbss_l:
|
|||
* initialization, now running from RAM.
|
||||
*/
|
||||
call_board_init_r:
|
||||
jal invalidate_icache_all
|
||||
jal flush_dcache_all
|
||||
la t0, board_init_r
|
||||
mv t4, t0 /* offset of board_init_r() */
|
||||
add t4, t4, t6 /* real address of board_init_r() */
|
||||
|
|
|
@ -7,6 +7,9 @@
|
|||
#ifndef _ASM_RISCV_CACHE_H
|
||||
#define _ASM_RISCV_CACHE_H
|
||||
|
||||
/* cache */
|
||||
void cache_flush(void);
|
||||
|
||||
/*
|
||||
* The current upper bound for RISCV L1 data cache line sizes is 32 bytes.
|
||||
* We use that value for aligning DMA buffers unless the board config has
|
||||
|
|
|
@ -6,8 +6,18 @@
|
|||
|
||||
#include <common.h>
|
||||
|
||||
void invalidate_icache_all(void)
|
||||
{
|
||||
asm volatile ("fence.i" ::: "memory");
|
||||
}
|
||||
|
||||
void flush_dcache_all(void)
|
||||
{
|
||||
asm volatile ("fence" :::"memory");
|
||||
}
|
||||
void flush_dcache_range(unsigned long start, unsigned long end)
|
||||
{
|
||||
flush_dcache_all();
|
||||
}
|
||||
|
||||
void invalidate_icache_range(unsigned long start, unsigned long end)
|
||||
|
@ -19,41 +29,45 @@ void invalidate_icache_range(unsigned long start, unsigned long end)
|
|||
invalidate_icache_all();
|
||||
}
|
||||
|
||||
void invalidate_icache_all(void)
|
||||
{
|
||||
asm volatile ("fence.i" ::: "memory");
|
||||
}
|
||||
|
||||
void invalidate_dcache_range(unsigned long start, unsigned long end)
|
||||
{
|
||||
flush_dcache_all();
|
||||
}
|
||||
|
||||
void cache_flush(void)
|
||||
{
|
||||
invalidate_icache_all();
|
||||
flush_dcache_all();
|
||||
}
|
||||
|
||||
void flush_cache(unsigned long addr, unsigned long size)
|
||||
{
|
||||
invalidate_icache_all();
|
||||
flush_dcache_all();
|
||||
}
|
||||
|
||||
void icache_enable(void)
|
||||
__weak void icache_enable(void)
|
||||
{
|
||||
}
|
||||
|
||||
void icache_disable(void)
|
||||
__weak void icache_disable(void)
|
||||
{
|
||||
}
|
||||
|
||||
int icache_status(void)
|
||||
__weak int icache_status(void)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dcache_enable(void)
|
||||
__weak void dcache_enable(void)
|
||||
{
|
||||
}
|
||||
|
||||
void dcache_disable(void)
|
||||
__weak void dcache_disable(void)
|
||||
{
|
||||
}
|
||||
|
||||
int dcache_status(void)
|
||||
__weak int dcache_status(void)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue