mirror of
git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2025-08-05 16:54:27 +00:00
RISC-V: Add Zicboz detection and block size parsing
Parse "riscv,cboz-block-size" from the DT by piggybacking on Zicbom's riscv_init_cbom_blocksize(). Additionally check the DT for the presence of the "zicboz" extension and, when it's present, validate the parsed cboz block size as we do Zicbom's cbom block size with riscv_isa_extension_check(). Signed-off-by: Andrew Jones <ajones@ventanamicro.com> Reviewed-by: Heiko Stuebner <heiko@sntech.de> Reviewed-by: Conor Dooley <conor.dooley@microchip.com> Link: https://lore.kernel.org/r/20230224162631.405473-5-ajones@ventanamicro.com Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
This commit is contained in:
parent
ea20f117ab
commit
7ea5a73617
6 changed files with 30 additions and 10 deletions
|
@ -50,7 +50,8 @@ void flush_icache_mm(struct mm_struct *mm, bool local);
|
||||||
#endif /* CONFIG_SMP */
|
#endif /* CONFIG_SMP */
|
||||||
|
|
||||||
extern unsigned int riscv_cbom_block_size;
|
extern unsigned int riscv_cbom_block_size;
|
||||||
void riscv_init_cbom_blocksize(void);
|
extern unsigned int riscv_cboz_block_size;
|
||||||
|
void riscv_init_cbo_blocksizes(void);
|
||||||
|
|
||||||
#ifdef CONFIG_RISCV_DMA_NONCOHERENT
|
#ifdef CONFIG_RISCV_DMA_NONCOHERENT
|
||||||
void riscv_noncoherent_supported(void);
|
void riscv_noncoherent_supported(void);
|
||||||
|
|
|
@ -42,6 +42,7 @@
|
||||||
#define RISCV_ISA_EXT_ZBB 30
|
#define RISCV_ISA_EXT_ZBB 30
|
||||||
#define RISCV_ISA_EXT_ZICBOM 31
|
#define RISCV_ISA_EXT_ZICBOM 31
|
||||||
#define RISCV_ISA_EXT_ZIHINTPAUSE 32
|
#define RISCV_ISA_EXT_ZIHINTPAUSE 32
|
||||||
|
#define RISCV_ISA_EXT_ZICBOZ 33
|
||||||
|
|
||||||
#define RISCV_ISA_EXT_MAX 64
|
#define RISCV_ISA_EXT_MAX 64
|
||||||
#define RISCV_ISA_EXT_NAME_LEN_MAX 32
|
#define RISCV_ISA_EXT_NAME_LEN_MAX 32
|
||||||
|
|
|
@ -186,6 +186,7 @@ arch_initcall(riscv_cpuinfo_init);
|
||||||
*/
|
*/
|
||||||
static struct riscv_isa_ext_data isa_ext_arr[] = {
|
static struct riscv_isa_ext_data isa_ext_arr[] = {
|
||||||
__RISCV_ISA_EXT_DATA(zicbom, RISCV_ISA_EXT_ZICBOM),
|
__RISCV_ISA_EXT_DATA(zicbom, RISCV_ISA_EXT_ZICBOM),
|
||||||
|
__RISCV_ISA_EXT_DATA(zicboz, RISCV_ISA_EXT_ZICBOZ),
|
||||||
__RISCV_ISA_EXT_DATA(zihintpause, RISCV_ISA_EXT_ZIHINTPAUSE),
|
__RISCV_ISA_EXT_DATA(zihintpause, RISCV_ISA_EXT_ZIHINTPAUSE),
|
||||||
__RISCV_ISA_EXT_DATA(zbb, RISCV_ISA_EXT_ZBB),
|
__RISCV_ISA_EXT_DATA(zbb, RISCV_ISA_EXT_ZBB),
|
||||||
__RISCV_ISA_EXT_DATA(sscofpmf, RISCV_ISA_EXT_SSCOFPMF),
|
__RISCV_ISA_EXT_DATA(sscofpmf, RISCV_ISA_EXT_SSCOFPMF),
|
||||||
|
|
|
@ -74,6 +74,15 @@ static bool riscv_isa_extension_check(int id)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
|
case RISCV_ISA_EXT_ZICBOZ:
|
||||||
|
if (!riscv_cboz_block_size) {
|
||||||
|
pr_err("Zicboz detected in ISA string, but no cboz-block-size found\n");
|
||||||
|
return false;
|
||||||
|
} else if (!is_power_of_2(riscv_cboz_block_size)) {
|
||||||
|
pr_err("cboz-block-size present, but is not a power-of-2\n");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
@ -222,6 +231,7 @@ void __init riscv_fill_hwcap(void)
|
||||||
SET_ISA_EXT_MAP("svpbmt", RISCV_ISA_EXT_SVPBMT);
|
SET_ISA_EXT_MAP("svpbmt", RISCV_ISA_EXT_SVPBMT);
|
||||||
SET_ISA_EXT_MAP("zbb", RISCV_ISA_EXT_ZBB);
|
SET_ISA_EXT_MAP("zbb", RISCV_ISA_EXT_ZBB);
|
||||||
SET_ISA_EXT_MAP("zicbom", RISCV_ISA_EXT_ZICBOM);
|
SET_ISA_EXT_MAP("zicbom", RISCV_ISA_EXT_ZICBOM);
|
||||||
|
SET_ISA_EXT_MAP("zicboz", RISCV_ISA_EXT_ZICBOZ);
|
||||||
SET_ISA_EXT_MAP("zihintpause", RISCV_ISA_EXT_ZIHINTPAUSE);
|
SET_ISA_EXT_MAP("zihintpause", RISCV_ISA_EXT_ZIHINTPAUSE);
|
||||||
}
|
}
|
||||||
#undef SET_ISA_EXT_MAP
|
#undef SET_ISA_EXT_MAP
|
||||||
|
|
|
@ -297,7 +297,7 @@ void __init setup_arch(char **cmdline_p)
|
||||||
setup_smp();
|
setup_smp();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
riscv_init_cbom_blocksize();
|
riscv_init_cbo_blocksizes();
|
||||||
riscv_fill_hwcap();
|
riscv_fill_hwcap();
|
||||||
apply_boot_alternatives();
|
apply_boot_alternatives();
|
||||||
if (IS_ENABLED(CONFIG_RISCV_ISA_ZICBOM) &&
|
if (IS_ENABLED(CONFIG_RISCV_ISA_ZICBOM) &&
|
||||||
|
|
|
@ -100,6 +100,9 @@ void flush_icache_pte(pte_t pte)
|
||||||
unsigned int riscv_cbom_block_size;
|
unsigned int riscv_cbom_block_size;
|
||||||
EXPORT_SYMBOL_GPL(riscv_cbom_block_size);
|
EXPORT_SYMBOL_GPL(riscv_cbom_block_size);
|
||||||
|
|
||||||
|
unsigned int riscv_cboz_block_size;
|
||||||
|
EXPORT_SYMBOL_GPL(riscv_cboz_block_size);
|
||||||
|
|
||||||
static void cbo_get_block_size(struct device_node *node,
|
static void cbo_get_block_size(struct device_node *node,
|
||||||
const char *name, u32 *block_size,
|
const char *name, u32 *block_size,
|
||||||
unsigned long *first_hartid)
|
unsigned long *first_hartid)
|
||||||
|
@ -122,19 +125,23 @@ static void cbo_get_block_size(struct device_node *node,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void riscv_init_cbom_blocksize(void)
|
void riscv_init_cbo_blocksizes(void)
|
||||||
{
|
{
|
||||||
|
unsigned long cbom_hartid, cboz_hartid;
|
||||||
|
u32 cbom_block_size = 0, cboz_block_size = 0;
|
||||||
struct device_node *node;
|
struct device_node *node;
|
||||||
unsigned long cbom_hartid;
|
|
||||||
u32 probed_block_size;
|
|
||||||
|
|
||||||
probed_block_size = 0;
|
|
||||||
for_each_of_cpu_node(node) {
|
for_each_of_cpu_node(node) {
|
||||||
/* set block-size for cbom extension if available */
|
/* set block-size for cbom and/or cboz extension if available */
|
||||||
cbo_get_block_size(node, "riscv,cbom-block-size",
|
cbo_get_block_size(node, "riscv,cbom-block-size",
|
||||||
&probed_block_size, &cbom_hartid);
|
&cbom_block_size, &cbom_hartid);
|
||||||
|
cbo_get_block_size(node, "riscv,cboz-block-size",
|
||||||
|
&cboz_block_size, &cboz_hartid);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (probed_block_size)
|
if (cbom_block_size)
|
||||||
riscv_cbom_block_size = probed_block_size;
|
riscv_cbom_block_size = cbom_block_size;
|
||||||
|
|
||||||
|
if (cboz_block_size)
|
||||||
|
riscv_cboz_block_size = cboz_block_size;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Reference in a new issue