Skip to content

Commit 6514f81

Browse files
SiFiveHollandpalmer-dabbelt
authored andcommitted
riscv: Fix CPU feature detection with SMP disabled
commit 914d6f4 ("RISC-V: only iterate over possible CPUs in ISA string parser") changed riscv_fill_hwcap() from iterating over CPU DT nodes to iterating over logical CPU IDs. Since this function runs long before cpu_dev_init() creates CPU devices, it hits the fallback path in of_cpu_device_node_get(), which itself iterates over the DT nodes, searching for a node with the requested CPU ID. (Incidentally, this makes riscv_fill_hwcap() now take quadratic time.) riscv_fill_hwcap() passes a logical CPU ID to of_cpu_device_node_get(), which uses the arch_match_cpu_phys_id() hook to translate the logical ID to a physical ID as found in the DT. arch_match_cpu_phys_id() has a generic weak definition, and RISC-V provides a strong definition using cpuid_to_hartid_map(). However, the RISC-V specific implementation is located in arch/riscv/kernel/smp.c, and that file is only compiled when SMP is enabled. As a result, when SMP is disabled, the generic definition is used, and riscv_isa gets initialized based on the ISA string of hart 0, not the boot hart. On FU740, this means has_fpu() returns false, and userspace crashes when trying to use floating-point instructions. Fix this by moving arch_match_cpu_phys_id() to a file which is always compiled. Fixes: 7011456 ("RISC-V: Add RISC-V specific arch_match_cpu_phys_id") Fixes: 914d6f4 ("RISC-V: only iterate over possible CPUs in ISA string parser") Reported-by: Palmer Dabbelt <[email protected]> Signed-off-by: Samuel Holland <[email protected]> Reviewed-by: Conor Dooley <[email protected]> Link: https://lore.kernel.org/r/[email protected] Cc: [email protected] Signed-off-by: Palmer Dabbelt <[email protected]>
1 parent c3bcc65 commit 6514f81

File tree

2 files changed

+5
-5
lines changed

2 files changed

+5
-5
lines changed

arch/riscv/kernel/cpu.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,11 @@
1717
#include <asm/smp.h>
1818
#include <asm/pgtable.h>
1919

20+
bool arch_match_cpu_phys_id(int cpu, u64 phys_id)
21+
{
22+
return phys_id == cpuid_to_hartid_map(cpu);
23+
}
24+
2025
/*
2126
* Returns the hart ID of the given device tree node, or -ENODEV if the node
2227
* isn't an enabled and valid RISC-V hart node.

arch/riscv/kernel/smp.c

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -61,11 +61,6 @@ int riscv_hartid_to_cpuid(unsigned long hartid)
6161
return -ENOENT;
6262
}
6363

64-
bool arch_match_cpu_phys_id(int cpu, u64 phys_id)
65-
{
66-
return phys_id == cpuid_to_hartid_map(cpu);
67-
}
68-
6964
static void ipi_stop(void)
7065
{
7166
set_cpu_online(smp_processor_id(), false);

0 commit comments

Comments
 (0)