Re: [PATCH v2] RISC-V: Add mvendorid, marchid, and mimpid to /proc/cpuinfo output

From: Ben Dooks
Date: Wed Jul 27 2022 - 06:12:24 EST


On 27/07/2022 11:06, Anup Patel wrote:
On Wed, Jul 27, 2022 at 2:25 PM Ben Dooks <ben.dooks@xxxxxxxxxxxxxxx> wrote:

On 27/07/2022 05:38, Anup Patel wrote:
Identifying the underlying RISC-V implementation can be important
for some of the user space applications. For example, the perf tool
uses arch specific CPU implementation id (i.e. CPUID) to select a
JSON file describing custom perf events on a CPU.

Currently, there is no way to identify RISC-V implementation so we
add mvendorid, marchid, and mimpid to /proc/cpuinfo output.

Signed-off-by: Anup Patel <apatel@xxxxxxxxxxxxxxxx>
Reviewed-by: Heinrich Schuchardt <heinrich.schuchardt@xxxxxxxxxxxxx>
Tested-by: Nikita Shubin <n.shubin@xxxxxxxxx>
---
Changes since v1:
- Use IS_ENABLED() to check CONFIG defines
- Added RB and TB tags in commit description
---
arch/riscv/kernel/cpu.c | 51 +++++++++++++++++++++++++++++++++++++++++
1 file changed, 51 insertions(+)

diff --git a/arch/riscv/kernel/cpu.c b/arch/riscv/kernel/cpu.c
index fba9e9f46a8c..04bcc91c91ea 100644
--- a/arch/riscv/kernel/cpu.c
+++ b/arch/riscv/kernel/cpu.c
@@ -3,10 +3,13 @@
* Copyright (C) 2012 Regents of the University of California
*/

+#include <linux/cpu.h>
#include <linux/init.h>
#include <linux/seq_file.h>
#include <linux/of.h>
+#include <asm/csr.h>
#include <asm/hwcap.h>
+#include <asm/sbi.h>
#include <asm/smp.h>
#include <asm/pgtable.h>

@@ -64,6 +67,50 @@ int riscv_of_parent_hartid(struct device_node *node)
}

#ifdef CONFIG_PROC_FS
+
+struct riscv_cpuinfo {
+ unsigned long mvendorid;
+ unsigned long marchid;
+ unsigned long mimpid;
+};
+static DEFINE_PER_CPU(struct riscv_cpuinfo, riscv_cpuinfo);
+
+static int riscv_cpuinfo_starting(unsigned int cpu)
+{
+ struct riscv_cpuinfo *ci = this_cpu_ptr(&riscv_cpuinfo);
+
+#if IS_ENABLED(CONFIG_RISCV_SBI)
+ ci->mvendorid = sbi_spec_is_0_1() ? 0 : sbi_get_mvendorid();
+ ci->marchid = sbi_spec_is_0_1() ? 0 : sbi_get_marchid();
+ ci->mimpid = sbi_spec_is_0_1() ? 0 : sbi_get_mimpid();

how about:

if (IS_ENABLED(CONFIG_RISCV_SBI)) {
...
} ... {

or maybe even:


if (IS_ENABLED(CONFIG_RISCV_SBI)) {
if (sbi_spec_is_0_1()) {
...
}
} ... {

would mean better compile coverage (at the slight exepnese of
having "false" sbi_spec_is_0_1() implemenation

Most of the sbi_xyz() functions are not available for NoMMU
kernel so using "if (IS_ENABLED())" results in compile error.

How about defining "false" versions for no-mmu case and try
and avoid these #if mountains?


+#elif IS_ENABLED(CONFIG_RISCV_M_MODE)
+ ci->mvendorid = csr_read(CSR_MVENDORID);
+ ci->marchid = csr_read(CSR_MARCHID);
+ ci->mimpid = csr_read(CSR_MIMPID);
+#else
+ ci->mvendorid = 0;
+ ci->marchid = 0;
+ ci->mimpid = 0;
+#endif

Would it be easier to zero out all the fields first and then fill them
in if supported?

Clearing out fields before "#if" ladder results in dead assignments.

Not sure which is worse here, the #if ladder or some possibly dead
assignments.

--
Ben Dooks http://www.codethink.co.uk/
Senior Engineer Codethink - Providing Genius

https://www.codethink.co.uk/privacy.html