git: f627ff51b76c - main - riscv/pmap.c: Don't pass hartid map to 'smp_rendezvous_cpus'
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Sat, 10 Oct 2026 12:36:52 UTC
The branch main has been updated by bnovkov:
URL: https://cgit.FreeBSD.org/src/commit/?id=f627ff51b76c728b8c6c4a7e5490ce3803c562ad
commit f627ff51b76c728b8c6c4a7e5490ce3803c562ad
Author: Bojan Novković <bnovkov@FreeBSD.org>
AuthorDate: 2026-09-27 18:25:22 +0000
Commit: Bojan Novković <bnovkov@FreeBSD.org>
CommitDate: 2026-10-10 12:34:57 +0000
riscv/pmap.c: Don't pass hartid map to 'smp_rendezvous_cpus'
The pm_active bitmask is indexed by hart IDs which can differ from
CPU IDs. `pmap_invalidate_range_svinval` assumes that the map is
indexed by CPU IDs, which is wrong and causes remote TLB invalidations
on unrelated CPUs.
Fix this by adding a routine that converts a hart-indexed bitmask
to a CPU ID-indexed bitmask. While we're here, fix a similar issue
in `pmap_active_cpus`.
Fixes: 99360212c739 ("riscv/pmap.c: Add an Svinval-aware variant of pmap_invalidate_range")
Reported by: markj
Reviewed by: markj, mhorne
Differential Revision: https://reviews.freebsd.org/D60072
---
sys/riscv/include/cpu.h | 3 +++
sys/riscv/include/smp.h | 1 -
sys/riscv/riscv/mp_machdep.c | 39 +++++++++++++++++++++++++++++++--------
sys/riscv/riscv/pmap.c | 11 ++++++-----
4 files changed, 40 insertions(+), 14 deletions(-)
diff --git a/sys/riscv/include/cpu.h b/sys/riscv/include/cpu.h
index 59214f05f595..05d3c4c834a5 100644
--- a/sys/riscv/include/cpu.h
+++ b/sys/riscv/include/cpu.h
@@ -36,6 +36,8 @@
#define _MACHINE_CPU_H_
#ifndef LOCORE
+#include <sys/_cpuset.h>
+
#include <machine/atomic.h>
#include <machine/cpufunc.h>
#include <machine/frame.h>
@@ -105,6 +107,7 @@ void cpu_reset(void) __dead2;
void fork_trampoline(void);
void identify_cpu(u_int cpu);
void printcpuinfo(u_int cpu);
+cpuset_t hartmask_to_cpumask(const cpuset_t);
static __inline uint64_t
get_cyclecount(void)
diff --git a/sys/riscv/include/smp.h b/sys/riscv/include/smp.h
index 863f0bbd6d21..bc1f77f32135 100644
--- a/sys/riscv/include/smp.h
+++ b/sys/riscv/include/smp.h
@@ -50,5 +50,4 @@ enum {
void ipi_all_but_self(u_int ipi);
void ipi_cpu(int cpu, u_int ipi);
void ipi_selected(cpuset_t cpus, u_int ipi);
-
#endif /* !_MACHINE_SMP_H_ */
diff --git a/sys/riscv/riscv/mp_machdep.c b/sys/riscv/riscv/mp_machdep.c
index 5402c6d388ed..1d5c85f8b13a 100644
--- a/sys/riscv/riscv/mp_machdep.c
+++ b/sys/riscv/riscv/mp_machdep.c
@@ -110,6 +110,19 @@ static volatile int aps_ready;
/* Temporary variables for init_secondary() */
void *dpcpu[MAXCPU - 1];
+static u_int
+hartid_to_cpuid(u_int hart)
+{
+ u_int cpuid;
+
+ cpuid = hart;
+ if (cpuid < boot_hart)
+ cpuid += mp_maxid + 1;
+ cpuid -= boot_hart;
+
+ return (cpuid);
+}
+
static void
release_aps(void *dummy __unused)
{
@@ -154,10 +167,7 @@ init_secondary(uint64_t hart)
u_int cpuid;
/* Renumber this cpu */
- cpuid = hart;
- if (cpuid < boot_hart)
- cpuid += mp_maxid + 1;
- cpuid -= boot_hart;
+ cpuid = hartid_to_cpuid(hart);
/* Setup the pcpu pointer */
pcpup = &__pcpu[cpuid];
@@ -366,10 +376,7 @@ cpu_init_fdt(u_int id, phandle_t node, u_int addr_size, pcell_t *reg)
* Rotate the CPU IDs to put the boot CPU as CPU 0.
* We keep the other CPUs ordered.
*/
- cpuid = hart;
- if (cpuid < boot_hart)
- cpuid += mp_maxid + 1;
- cpuid -= boot_hart;
+ cpuid = hartid_to_cpuid(hart);
/* Check if we are able to start this cpu */
if (cpuid > mp_maxid)
@@ -525,3 +532,19 @@ ipi_selected(cpuset_t cpus, u_int ipi)
CTR1(KTR_SMP, "ipi_selected: ipi: %x", ipi);
intr_ipi_send(cpus, ipi);
}
+
+cpuset_t
+hartmask_to_cpumask(const cpuset_t harts)
+{
+ u_int hart;
+ u_int cpu;
+ cpuset_t cpumask;
+
+ CPU_ZERO(&cpumask);
+ CPU_FOREACH_ISSET(hart, &harts) {
+ cpu = hartid_to_cpuid(hart);
+ CPU_SET(cpu, &cpumask);
+ }
+
+ return (cpumask);
+}
diff --git a/sys/riscv/riscv/pmap.c b/sys/riscv/riscv/pmap.c
index b3f03eeaab9f..66dd65747f13 100644
--- a/sys/riscv/riscv/pmap.c
+++ b/sys/riscv/riscv/pmap.c
@@ -157,6 +157,7 @@
#include <vm/vm_dumpset.h>
#include <vm/uma.h>
+#include <machine/cpu.h>
#include <machine/machdep.h>
#include <machine/md_var.h>
#include <machine/ifunc.h>
@@ -1149,11 +1150,11 @@ pmap_invalidate_range_svinval(pmap_t pmap, vm_offset_t sva, vm_offset_t eva)
args.sva = sva;
args.eva = eva;
fence();
- if (smp_started)
- smp_rendezvous_cpus(pmap->pm_active, smp_no_rendezvous_barrier,
- pmap_invalidate_range_svinval_cb,
+ if (smp_started) {
+ smp_rendezvous_cpus(hartmask_to_cpumask(pmap->pm_active),
+ smp_no_rendezvous_barrier, pmap_invalidate_range_svinval_cb,
smp_no_rendezvous_barrier, &args);
- else
+ } else
pmap_invalidate_range_svinval_cb(&args);
sched_unpin();
}
@@ -5323,7 +5324,7 @@ pmap_activate_boot(pmap_t pmap)
void
pmap_active_cpus(pmap_t pmap, cpuset_t *res)
{
- *res = pmap->pm_active;
+ *res = hartmask_to_cpumask(pmap->pm_active);
}
void