* [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART
@ 2026-04-25 0:59 guoren
2026-04-25 0:59 ` [PATCH V2 1/4] RISC-V: KVM: AIA: Make HGEI number and management fully per-CPU guoren
` (5 more replies)
0 siblings, 6 replies; 13+ messages in thread
From: guoren @ 2026-04-25 0:59 UTC (permalink / raw)
To: guoren
Cc: alex, anup, aou, atish.patra, cp0613, fangyu.yu, gaohan,
inochiama, kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer,
pjw, tglx
From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
This short series converts RISC-V KVM AIA's Hypervisor Guest External
Interrupt (HGEI) line management from a global "one-size-fits-all"
model to a fully per-HART (per-CPU) model. It also performs the
corresponding cleanup in the IMSIC irqchip driver.
The motivation is to properly support heterogeneous RISC-V SoCs
(big.LITTLE, multi-vendor core mixes) where different HARTs may
expose different numbers of guest interrupt files / HGEIE bits.
The old global `kvm_riscv_aia_nr_hgei` and
`imsic_global_config::nr_guest_files` assumptions are no longer
tenable and are removed.
After this series, HGEI allocation, freeing, and interrupt delivery
are completely per-HART, the code is simpler and clearer, and there
are no remaining global assumptions about guest interrupt file
counts.
Changelog:
V2:
- Add per-HART IMSIC guest files to compute final HGEI count.
- Add min(local->nr_guest_files, nr_guest_files);
V1:
https://lore.kernel.org/kvm-riscv/20260421145451.1597930-1-guoren@kernel.org/
Guo Ren (Alibaba DAMO Academy) (4):
RISC-V: KVM: AIA: Make HGEI number and management fully per-CPU
RISC-V: KVM: AIA: Replace global HGEI count with simple enabled bool
irqchip/riscv-imsic: Move nr_guest_files to per-HART local config
RISC-V: KVM: AIA: Use per-HART IMSIC guest files to compute final HGEI
count
arch/riscv/include/asm/kvm_aia.h | 2 +-
arch/riscv/kvm/aia.c | 66 +++++++++++++++----------
arch/riscv/kvm/aia_device.c | 4 +-
arch/riscv/kvm/main.c | 3 +-
drivers/irqchip/irq-riscv-imsic-state.c | 10 ++--
include/linux/irqchip/riscv-imsic.h | 6 +--
6 files changed, 53 insertions(+), 38 deletions(-)
--
2.43.0
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH V2 1/4] RISC-V: KVM: AIA: Make HGEI number and management fully per-CPU
2026-04-25 0:59 [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART guoren
@ 2026-04-25 0:59 ` guoren
2026-05-24 5:23 ` Anup Patel
2026-04-25 0:59 ` [PATCH V2 2/4] RISC-V: KVM: AIA: Replace global HGEI count with simple enabled bool guoren
` (4 subsequent siblings)
5 siblings, 1 reply; 13+ messages in thread
From: guoren @ 2026-04-25 0:59 UTC (permalink / raw)
To: guoren
Cc: alex, anup, aou, atish.patra, cp0613, fangyu.yu, gaohan,
inochiama, kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer,
pjw, tglx
From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
Previously the number of Hypervisor Guest External Interrupt (HGEI)
lines was stored in a single global variable `kvm_riscv_aia_nr_hgei`
and assumed to be the same for all HARTs. This assumption does not
hold on heterogeneous RISC-V SoCs where different cores may expose
different HGEIE CSR widths.
Introduce `nr_hgei` field into the per-CPU `struct aia_hgei_control`
and probe the actual supported HGEI count for the current HART in
`kvm_riscv_aia_enable()` using the standard RISC-V CSR probe
technique:
csr_write(CSR_HGEIE, -1UL);
nr = fls_long(csr_read(CSR_HGEIE));
if (nr)
nr--;
All HGEI allocation, free and disable paths (`kvm_riscv_aia_free_hgei()`,
`kvm_riscv_aia_disable()`, etc.) now use the per-CPU value instead of
the global one.
The early global `kvm_riscv_aia_nr_hgei` is kept only for deciding
whether SGEI interrupt registration is needed; the real per-HART
initialization of lock and free_bitmap is moved to enable time.
This makes KVM AIA robust on big.LITTLE-style and multi-vendor
asymmetric platforms.
Signed-off-by: Guo Ren (Alibaba DAMO Academy) <guoren@kernel.org>
---
arch/riscv/kvm/aia.c | 40 ++++++++++++++++++++++++----------------
1 file changed, 24 insertions(+), 16 deletions(-)
diff --git a/arch/riscv/kvm/aia.c b/arch/riscv/kvm/aia.c
index 5ec503288555..a23729052cfb 100644
--- a/arch/riscv/kvm/aia.c
+++ b/arch/riscv/kvm/aia.c
@@ -23,6 +23,7 @@ struct aia_hgei_control {
raw_spinlock_t lock;
unsigned long free_bitmap;
struct kvm_vcpu *owners[BITS_PER_LONG];
+ unsigned int nr_hgei;
};
static DEFINE_PER_CPU(struct aia_hgei_control, aia_hgei);
static int hgei_parent_irq;
@@ -452,7 +453,7 @@ void kvm_riscv_aia_free_hgei(int cpu, int hgei)
raw_spin_lock_irqsave(&hgctrl->lock, flags);
- if (hgei > 0 && hgei <= kvm_riscv_aia_nr_hgei) {
+ if (hgei > 0 && hgei <= hgctrl->nr_hgei) {
if (!(hgctrl->free_bitmap & BIT(hgei))) {
hgctrl->free_bitmap |= BIT(hgei);
hgctrl->owners[hgei] = NULL;
@@ -486,21 +487,8 @@ static irqreturn_t hgei_interrupt(int irq, void *dev_id)
static int aia_hgei_init(void)
{
- int cpu, rc;
+ int rc;
struct irq_domain *domain;
- struct aia_hgei_control *hgctrl;
-
- /* Initialize per-CPU guest external interrupt line management */
- for_each_possible_cpu(cpu) {
- hgctrl = per_cpu_ptr(&aia_hgei, cpu);
- raw_spin_lock_init(&hgctrl->lock);
- if (kvm_riscv_aia_nr_hgei) {
- hgctrl->free_bitmap =
- BIT(kvm_riscv_aia_nr_hgei + 1) - 1;
- hgctrl->free_bitmap &= ~BIT(0);
- } else
- hgctrl->free_bitmap = 0;
- }
/* Skip SGEI interrupt setup for zero guest external interrupts */
if (!kvm_riscv_aia_nr_hgei)
@@ -545,9 +533,29 @@ static void aia_hgei_exit(void)
void kvm_riscv_aia_enable(void)
{
+ struct aia_hgei_control *hgctrl;
+
if (!kvm_riscv_aia_available())
return;
+ hgctrl = this_cpu_ptr(&aia_hgei);
+
+ /* Figure-out number of bits in HGEIE */
+ csr_write(CSR_HGEIE, -1UL);
+ hgctrl->nr_hgei = fls_long(csr_read(CSR_HGEIE));
+ csr_write(CSR_HGEIE, 0);
+ if (hgctrl->nr_hgei)
+ hgctrl->nr_hgei--;
+
+ if (hgctrl->nr_hgei) {
+ hgctrl->free_bitmap = BIT(hgctrl->nr_hgei + 1) - 1;
+ hgctrl->free_bitmap &= ~BIT(0);
+ } else {
+ hgctrl->free_bitmap = 0;
+ }
+
+ raw_spin_lock_init(&hgctrl->lock);
+
csr_write(CSR_HVICTL, aia_hvictl_value(false));
csr_write(CSR_HVIPRIO1, 0x0);
csr_write(CSR_HVIPRIO2, 0x0);
@@ -588,7 +596,7 @@ void kvm_riscv_aia_disable(void)
raw_spin_lock_irqsave(&hgctrl->lock, flags);
- for (i = 0; i <= kvm_riscv_aia_nr_hgei; i++) {
+ for (i = 0; i <= hgctrl->nr_hgei; i++) {
vcpu = hgctrl->owners[i];
if (!vcpu)
continue;
--
2.43.0
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH V2 2/4] RISC-V: KVM: AIA: Replace global HGEI count with simple enabled bool
2026-04-25 0:59 [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART guoren
2026-04-25 0:59 ` [PATCH V2 1/4] RISC-V: KVM: AIA: Make HGEI number and management fully per-CPU guoren
@ 2026-04-25 0:59 ` guoren
2026-05-24 5:24 ` Anup Patel
2026-04-25 0:59 ` [PATCH V2 3/4] irqchip/riscv-imsic: Move nr_guest_files to per-HART local config guoren
` (3 subsequent siblings)
5 siblings, 1 reply; 13+ messages in thread
From: guoren @ 2026-04-25 0:59 UTC (permalink / raw)
To: guoren
Cc: alex, anup, aou, atish.patra, cp0613, fangyu.yu, gaohan,
inochiama, kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer,
pjw, tglx
From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
Now that HGEI line management is fully per-CPU (via struct
aia_hgei_control::nr_hgei), the global `kvm_riscv_aia_nr_hgei`
is no longer needed. Replace it with a simple `bool
kvm_riscv_aia_hgei_enabled` that only indicates whether HGEI
support is available at all.
Signed-off-by: Guo Ren (Alibaba DAMO Academy) <guoren@kernel.org>
---
arch/riscv/include/asm/kvm_aia.h | 2 +-
arch/riscv/kvm/aia.c | 18 ++++++++----------
arch/riscv/kvm/aia_device.c | 4 ++--
arch/riscv/kvm/main.c | 3 +--
4 files changed, 12 insertions(+), 15 deletions(-)
diff --git a/arch/riscv/include/asm/kvm_aia.h b/arch/riscv/include/asm/kvm_aia.h
index b04ecdd1a860..e8749ac6bed7 100644
--- a/arch/riscv/include/asm/kvm_aia.h
+++ b/arch/riscv/include/asm/kvm_aia.h
@@ -79,7 +79,7 @@ struct kvm_vcpu_aia {
#define irqchip_in_kernel(k) ((k)->arch.aia.in_kernel)
-extern unsigned int kvm_riscv_aia_nr_hgei;
+extern bool kvm_riscv_aia_hgei_enabled;
extern unsigned int kvm_riscv_aia_max_ids;
DECLARE_STATIC_KEY_FALSE(kvm_riscv_aia_available);
#define kvm_riscv_aia_available() \
diff --git a/arch/riscv/kvm/aia.c b/arch/riscv/kvm/aia.c
index a23729052cfb..70ff1d25dd99 100644
--- a/arch/riscv/kvm/aia.c
+++ b/arch/riscv/kvm/aia.c
@@ -28,7 +28,7 @@ struct aia_hgei_control {
static DEFINE_PER_CPU(struct aia_hgei_control, aia_hgei);
static int hgei_parent_irq;
-unsigned int kvm_riscv_aia_nr_hgei;
+bool kvm_riscv_aia_hgei_enabled;
unsigned int kvm_riscv_aia_max_ids;
DEFINE_STATIC_KEY_FALSE(kvm_riscv_aia_available);
@@ -491,7 +491,7 @@ static int aia_hgei_init(void)
struct irq_domain *domain;
/* Skip SGEI interrupt setup for zero guest external interrupts */
- if (!kvm_riscv_aia_nr_hgei)
+ if (!kvm_riscv_aia_hgei_enabled)
goto skip_sgei_interrupt;
/* Find INTC irq domain */
@@ -524,7 +524,7 @@ static int aia_hgei_init(void)
static void aia_hgei_exit(void)
{
/* Do nothing for zero guest external interrupts */
- if (!kvm_riscv_aia_nr_hgei)
+ if (!kvm_riscv_aia_hgei_enabled)
return;
/* Free per-CPU SGEI interrupt */
@@ -631,6 +631,7 @@ int kvm_riscv_aia_init(void)
{
int rc;
const struct imsic_global_config *gc;
+ unsigned int kvm_riscv_aia_nr_hgei;
if (!riscv_isa_extension_available(NULL, SxAIA))
return -ENODEV;
@@ -641,21 +642,18 @@ int kvm_riscv_aia_init(void)
kvm_riscv_aia_nr_hgei = fls_long(csr_read(CSR_HGEIE));
csr_write(CSR_HGEIE, 0);
if (kvm_riscv_aia_nr_hgei)
- kvm_riscv_aia_nr_hgei--;
+ kvm_riscv_aia_hgei_enabled = true;
/*
* Number of usable HGEI lines should be minimum of per-HART
* IMSIC guest files and number of bits in HGEIE
*/
- if (gc)
- kvm_riscv_aia_nr_hgei = min((ulong)kvm_riscv_aia_nr_hgei,
- gc->nr_guest_files);
- else
- kvm_riscv_aia_nr_hgei = 0;
+ if (!gc)
+ kvm_riscv_aia_hgei_enabled = 0;
/* Find number of guest MSI IDs */
kvm_riscv_aia_max_ids = IMSIC_MAX_ID;
- if (gc && kvm_riscv_aia_nr_hgei)
+ if (gc && kvm_riscv_aia_hgei_enabled)
kvm_riscv_aia_max_ids = gc->nr_guest_ids + 1;
/* Initialize guest external interrupt line management */
diff --git a/arch/riscv/kvm/aia_device.c b/arch/riscv/kvm/aia_device.c
index 3d1e81e2a36b..5b45b1114425 100644
--- a/arch/riscv/kvm/aia_device.c
+++ b/arch/riscv/kvm/aia_device.c
@@ -71,7 +71,7 @@ static int aia_config(struct kvm *kvm, unsigned long type,
* external interrupts (i.e. non-zero
* VS-level IMSIC pages).
*/
- if (!kvm_riscv_aia_nr_hgei)
+ if (!kvm_riscv_aia_hgei_enabled)
return -EINVAL;
break;
default:
@@ -628,7 +628,7 @@ void kvm_riscv_aia_init_vm(struct kvm *kvm)
*/
/* Initialize default values in AIA global context */
- aia->mode = (kvm_riscv_aia_nr_hgei) ?
+ aia->mode = (kvm_riscv_aia_hgei_enabled) ?
KVM_DEV_RISCV_AIA_MODE_AUTO : KVM_DEV_RISCV_AIA_MODE_EMUL;
aia->nr_ids = kvm_riscv_aia_max_ids - 1;
aia->nr_sources = 0;
diff --git a/arch/riscv/kvm/main.c b/arch/riscv/kvm/main.c
index cb8a65273c1f..bcfa139f4871 100644
--- a/arch/riscv/kvm/main.c
+++ b/arch/riscv/kvm/main.c
@@ -169,8 +169,7 @@ static int __init riscv_kvm_init(void)
kvm_info("VMID %ld bits available\n", kvm_riscv_gstage_vmid_bits());
if (kvm_riscv_aia_available())
- kvm_info("AIA available with %d guest external interrupts\n",
- kvm_riscv_aia_nr_hgei);
+ kvm_info("AIA available with guest external interrupts\n");
kvm_riscv_setup_vendor_features();
--
2.43.0
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH V2 3/4] irqchip/riscv-imsic: Move nr_guest_files to per-HART local config
2026-04-25 0:59 [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART guoren
2026-04-25 0:59 ` [PATCH V2 1/4] RISC-V: KVM: AIA: Make HGEI number and management fully per-CPU guoren
2026-04-25 0:59 ` [PATCH V2 2/4] RISC-V: KVM: AIA: Replace global HGEI count with simple enabled bool guoren
@ 2026-04-25 0:59 ` guoren
2026-05-05 20:12 ` Thomas Gleixner
2026-04-25 0:59 ` [PATCH V2 4/4] RISC-V: KVM: AIA: Use per-HART IMSIC guest files to compute final HGEI count guoren
` (2 subsequent siblings)
5 siblings, 1 reply; 13+ messages in thread
From: guoren @ 2026-04-25 0:59 UTC (permalink / raw)
To: guoren
Cc: alex, anup, aou, atish.patra, cp0613, fangyu.yu, gaohan,
inochiama, kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer,
pjw, tglx
From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
With the recent KVM AIA per-HART HGEI conversion, the global
nr_guest_files is no longer appropriate. Different HARTs in
heterogeneous SoCs may have different numbers of guest interrupt
files.
Move `nr_guest_files` from `struct imsic_global_config` to
`struct imsic_local_config`, and compute it per-CPU in
imsic_setup_state() based on the actual MMIO guest file region size.
Update the related comment to reflect that KVM now uses the
per-HART value.
This eliminates the last global assumption about guest files and
completes the per-HART conversion series for RISC-V AIA/IMSIC.
Signed-off-by: Guo Ren (Alibaba DAMO Academy) <guoren@kernel.org>
---
drivers/irqchip/irq-riscv-imsic-state.c | 10 ++++++----
include/linux/irqchip/riscv-imsic.h | 6 +++---
2 files changed, 9 insertions(+), 7 deletions(-)
diff --git a/drivers/irqchip/irq-riscv-imsic-state.c b/drivers/irqchip/irq-riscv-imsic-state.c
index e3ed874d89e7..f01525362cf7 100644
--- a/drivers/irqchip/irq-riscv-imsic-state.c
+++ b/drivers/irqchip/irq-riscv-imsic-state.c
@@ -878,7 +878,6 @@ int __init imsic_setup_state(struct fwnode_handle *fwnode, void *opaque)
}
/* Configure handlers for target CPUs */
- global->nr_guest_files = BIT(global->guest_index_bits) - 1;
for (i = 0; i < nr_parent_irqs; i++) {
rc = imsic_get_parent_hartid(fwnode, i, &hartid);
if (rc) {
@@ -910,23 +909,26 @@ int __init imsic_setup_state(struct fwnode_handle *fwnode, void *opaque)
reloff -= ALIGN(resource_size(&mmios[j]),
BIT(global->guest_index_bits) * IMSIC_MMIO_PAGE_SZ);
}
+
+ local = per_cpu_ptr(global->local, cpu);
+ local->nr_guest_files = BIT(global->guest_index_bits) - 1;
+
if (index >= nr_mmios) {
pr_warn("%pfwP: MMIO not found for parent irq%d\n", fwnode, i);
continue;
}
- local = per_cpu_ptr(global->local, cpu);
local->msi_pa = mmios[index].start + reloff;
local->msi_va = mmios_va[index] + reloff;
/*
- * KVM uses global->nr_guest_files to determine the available guest
+ * KVM uses local->nr_guest_files to determine the available guest
* interrupt files on each CPU. Take the minimum number of guest
* interrupt files across all CPUs to avoid KVM incorrectly allocating
* an unexisted or unmapped guest interrupt file on some CPUs.
*/
nr_guest_files = (resource_size(&mmios[index]) - reloff) / IMSIC_MMIO_PAGE_SZ - 1;
- global->nr_guest_files = min(global->nr_guest_files, nr_guest_files);
+ local->nr_guest_files = min(local->nr_guest_files, nr_guest_files);
nr_handlers++;
}
diff --git a/include/linux/irqchip/riscv-imsic.h b/include/linux/irqchip/riscv-imsic.h
index 4b348836de7a..13e8bd7ff4b4 100644
--- a/include/linux/irqchip/riscv-imsic.h
+++ b/include/linux/irqchip/riscv-imsic.h
@@ -40,6 +40,9 @@
struct imsic_local_config {
phys_addr_t msi_pa;
void __iomem *msi_va;
+
+ /* Number of guest interrupt files per core */
+ u32 nr_guest_files;
};
struct imsic_global_config {
@@ -68,9 +71,6 @@ struct imsic_global_config {
/* Number of guest interrupt identities */
u32 nr_guest_ids;
- /* Number of guest interrupt files per core */
- u32 nr_guest_files;
-
/* Per-CPU IMSIC addresses */
struct imsic_local_config __percpu *local;
};
--
2.43.0
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH V2 4/4] RISC-V: KVM: AIA: Use per-HART IMSIC guest files to compute final HGEI count
2026-04-25 0:59 [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART guoren
` (2 preceding siblings ...)
2026-04-25 0:59 ` [PATCH V2 3/4] irqchip/riscv-imsic: Move nr_guest_files to per-HART local config guoren
@ 2026-04-25 0:59 ` guoren
2026-04-25 1:06 ` Re: [PATCH 3/3] irqchip/riscv-imsic: Remove global nr_guest_files after KVM AIA per-HART conversion guoren
2026-05-24 5:25 ` [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART Anup Patel
5 siblings, 0 replies; 13+ messages in thread
From: guoren @ 2026-04-25 0:59 UTC (permalink / raw)
To: guoren
Cc: alex, anup, aou, atish.patra, cp0613, fangyu.yu, gaohan,
inochiama, kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer,
pjw, tglx
From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
Now that `nr_guest_files` has been moved to `struct imsic_local_config`
and is computed per-HART, KVM must respect the actual number of guest
interrupt files available on each HART when setting up HGEI.
In `kvm_riscv_aia_enable()`:
- Retrieve the per-CPU IMSIC local config
- Take `min(hgctrl->nr_hgei, lc->nr_guest_files)` as the final usable
HGEI count for this HART
- Use the result to initialize `free_bitmap`
This ensures correct HGEI allocation on heterogeneous RISC-V SoCs
where different cores may have different IMSIC guest file counts, and
completes the per-HART conversion series.
Signed-off-by: Guo Ren (Alibaba DAMO Academy) <guoren@kernel.org>
---
arch/riscv/kvm/aia.c | 12 ++++++++++--
1 file changed, 10 insertions(+), 2 deletions(-)
diff --git a/arch/riscv/kvm/aia.c b/arch/riscv/kvm/aia.c
index 70ff1d25dd99..a5f4b7fe1dce 100644
--- a/arch/riscv/kvm/aia.c
+++ b/arch/riscv/kvm/aia.c
@@ -534,6 +534,9 @@ static void aia_hgei_exit(void)
void kvm_riscv_aia_enable(void)
{
struct aia_hgei_control *hgctrl;
+ const struct imsic_global_config *gc;
+ const struct imsic_local_config *lc;
+ unsigned int nr_hgei;
if (!kvm_riscv_aia_available())
return;
@@ -547,8 +550,13 @@ void kvm_riscv_aia_enable(void)
if (hgctrl->nr_hgei)
hgctrl->nr_hgei--;
- if (hgctrl->nr_hgei) {
- hgctrl->free_bitmap = BIT(hgctrl->nr_hgei + 1) - 1;
+ gc = imsic_get_global_config();
+ lc = (gc) ? this_cpu_ptr(gc->local) : NULL;
+ if (lc)
+ nr_hgei = min(hgctrl->nr_hgei, lc->nr_guest_files);
+
+ if (nr_hgei) {
+ hgctrl->free_bitmap = BIT(nr_hgei + 1) - 1;
hgctrl->free_bitmap &= ~BIT(0);
} else {
hgctrl->free_bitmap = 0;
--
2.43.0
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply related [flat|nested] 13+ messages in thread
* Re: Re: [PATCH 3/3] irqchip/riscv-imsic: Remove global nr_guest_files after KVM AIA per-HART conversion
2026-04-25 0:59 [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART guoren
` (3 preceding siblings ...)
2026-04-25 0:59 ` [PATCH V2 4/4] RISC-V: KVM: AIA: Use per-HART IMSIC guest files to compute final HGEI count guoren
@ 2026-04-25 1:06 ` guoren
2026-05-24 5:25 ` [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART Anup Patel
5 siblings, 0 replies; 13+ messages in thread
From: guoren @ 2026-04-25 1:06 UTC (permalink / raw)
To: guoren
Cc: alex, anup, aou, atish.patra, cp0613, fangyu.yu, gaohan,
inochiama, kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer,
pjw, tglx
Hi Anup,
> On Wed, Apr 22, 2026 at 8:39 AM Guo Ren <guoren@kernel.org> wrote:
> >
> > Hi all,
> >
> > This patch simply removed `nr_guest_files`, which is suboptimal. For
> > v2, I will keep `nr_guest_files` inside `struct imsic_local_config`
> > (per-HART) and compute the effective HGEI count in
> > `kvm_riscv_aia_enable()` as:
> >
> > min(hgctrl->nr_hgei, lc->nr_guest_files)
>
> Yes, I was going to comment the exact same thing. Good that you
> realized it early.
Thank you for the feedback. This is V2:
https://lore.kernel.org/kvm-riscv/20260425005916.3321811-1-guoren@kernel.org/
Best Regards
GUO Ren
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH V2 3/4] irqchip/riscv-imsic: Move nr_guest_files to per-HART local config
2026-04-25 0:59 ` [PATCH V2 3/4] irqchip/riscv-imsic: Move nr_guest_files to per-HART local config guoren
@ 2026-05-05 20:12 ` Thomas Gleixner
2026-05-07 10:04 ` Guo Ren
2026-05-07 12:01 ` Anup Patel
0 siblings, 2 replies; 13+ messages in thread
From: Thomas Gleixner @ 2026-05-05 20:12 UTC (permalink / raw)
To: guoren, guoren
Cc: alex, anup, aou, atish.patra, cp0613, fangyu.yu, gaohan,
inochiama, kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer,
pjw
On Sat, Apr 25 2026 at 00:59, guoren@kernel.org wrote:
> From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
>
> With the recent KVM AIA per-HART HGEI conversion, the global
> nr_guest_files is no longer appropriate. Different HARTs in
> heterogeneous SoCs may have different numbers of guest interrupt
> files.
>
> Move `nr_guest_files` from `struct imsic_global_config` to
> `struct imsic_local_config`, and compute it per-CPU in
> imsic_setup_state() based on the actual MMIO guest file region size.
>
> Update the related comment to reflect that KVM now uses the
> per-HART value.
>
> This eliminates the last global assumption about guest files and
> completes the per-HART conversion series for RISC-V AIA/IMSIC.
>
> Signed-off-by: Guo Ren (Alibaba DAMO Academy) <guoren@kernel.org>
Assuming this goes through the risc-v tree:
Acked-by: Thomas Gleixner <tglx@kernel.org>
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH V2 3/4] irqchip/riscv-imsic: Move nr_guest_files to per-HART local config
2026-05-05 20:12 ` Thomas Gleixner
@ 2026-05-07 10:04 ` Guo Ren
2026-05-07 12:01 ` Anup Patel
1 sibling, 0 replies; 13+ messages in thread
From: Guo Ren @ 2026-05-07 10:04 UTC (permalink / raw)
To: Thomas Gleixner
Cc: alex, anup, aou, atish.patra, cp0613, fangyu.yu, gaohan,
inochiama, kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer,
pjw
On Wed, May 6, 2026 at 4:12 AM Thomas Gleixner <tglx@kernel.org> wrote:
>
> On Sat, Apr 25 2026 at 00:59, guoren@kernel.org wrote:
> > From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
> >
> > With the recent KVM AIA per-HART HGEI conversion, the global
> > nr_guest_files is no longer appropriate. Different HARTs in
> > heterogeneous SoCs may have different numbers of guest interrupt
> > files.
> >
> > Move `nr_guest_files` from `struct imsic_global_config` to
> > `struct imsic_local_config`, and compute it per-CPU in
> > imsic_setup_state() based on the actual MMIO guest file region size.
> >
> > Update the related comment to reflect that KVM now uses the
> > per-HART value.
> >
> > This eliminates the last global assumption about guest files and
> > completes the per-HART conversion series for RISC-V AIA/IMSIC.
> >
> > Signed-off-by: Guo Ren (Alibaba DAMO Academy) <guoren@kernel.org>
>
> Assuming this goes through the risc-v tree:
>
> Acked-by: Thomas Gleixner <tglx@kernel.org>
Got it & Thx Thomas.
I think it'll go through the kvm-riscv tree because it's all about kvm
improvements.
--
Best Regards
Guo Ren
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH V2 3/4] irqchip/riscv-imsic: Move nr_guest_files to per-HART local config
2026-05-05 20:12 ` Thomas Gleixner
2026-05-07 10:04 ` Guo Ren
@ 2026-05-07 12:01 ` Anup Patel
1 sibling, 0 replies; 13+ messages in thread
From: Anup Patel @ 2026-05-07 12:01 UTC (permalink / raw)
To: Thomas Gleixner
Cc: guoren, alex, aou, atish.patra, cp0613, fangyu.yu, gaohan,
inochiama, kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer,
pjw
Hi Thomas,
On Wed, May 6, 2026 at 1:42 AM Thomas Gleixner <tglx@kernel.org> wrote:
>
> On Sat, Apr 25 2026 at 00:59, guoren@kernel.org wrote:
> > From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
> >
> > With the recent KVM AIA per-HART HGEI conversion, the global
> > nr_guest_files is no longer appropriate. Different HARTs in
> > heterogeneous SoCs may have different numbers of guest interrupt
> > files.
> >
> > Move `nr_guest_files` from `struct imsic_global_config` to
> > `struct imsic_local_config`, and compute it per-CPU in
> > imsic_setup_state() based on the actual MMIO guest file region size.
> >
> > Update the related comment to reflect that KVM now uses the
> > per-HART value.
> >
> > This eliminates the last global assumption about guest files and
> > completes the per-HART conversion series for RISC-V AIA/IMSIC.
> >
> > Signed-off-by: Guo Ren (Alibaba DAMO Academy) <guoren@kernel.org>
>
> Assuming this goes through the risc-v tree:
>
> Acked-by: Thomas Gleixner <tglx@kernel.org>
Thanks, I will take this series through KVM RISC-V tree.
Regards,
Anup
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH V2 1/4] RISC-V: KVM: AIA: Make HGEI number and management fully per-CPU
2026-04-25 0:59 ` [PATCH V2 1/4] RISC-V: KVM: AIA: Make HGEI number and management fully per-CPU guoren
@ 2026-05-24 5:23 ` Anup Patel
2026-05-26 1:08 ` Guo Ren
0 siblings, 1 reply; 13+ messages in thread
From: Anup Patel @ 2026-05-24 5:23 UTC (permalink / raw)
To: guoren
Cc: alex, aou, atish.patra, cp0613, fangyu.yu, gaohan, inochiama,
kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer, pjw, tglx
On Sat, Apr 25, 2026 at 6:29 AM <guoren@kernel.org> wrote:
>
> From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
>
> Previously the number of Hypervisor Guest External Interrupt (HGEI)
> lines was stored in a single global variable `kvm_riscv_aia_nr_hgei`
> and assumed to be the same for all HARTs. This assumption does not
> hold on heterogeneous RISC-V SoCs where different cores may expose
> different HGEIE CSR widths.
>
> Introduce `nr_hgei` field into the per-CPU `struct aia_hgei_control`
> and probe the actual supported HGEI count for the current HART in
> `kvm_riscv_aia_enable()` using the standard RISC-V CSR probe
> technique:
>
> csr_write(CSR_HGEIE, -1UL);
> nr = fls_long(csr_read(CSR_HGEIE));
> if (nr)
> nr--;
>
> All HGEI allocation, free and disable paths (`kvm_riscv_aia_free_hgei()`,
> `kvm_riscv_aia_disable()`, etc.) now use the per-CPU value instead of
> the global one.
>
> The early global `kvm_riscv_aia_nr_hgei` is kept only for deciding
> whether SGEI interrupt registration is needed; the real per-HART
> initialization of lock and free_bitmap is moved to enable time.
We should keep the `kvm_riscv_aia_nr_hgei` to imply two things:
1) Minimum number of HGEI lines available across all HARTs
2) Non-zero kvm_riscv_aia_nr_hgei means HGEI is enabled
The PATCH2 is redundant and must be droped. I will take care
care of this at the time of merging.
>
> This makes KVM AIA robust on big.LITTLE-style and multi-vendor
> asymmetric platforms.
>
> Signed-off-by: Guo Ren (Alibaba DAMO Academy) <guoren@kernel.org>
> ---
> arch/riscv/kvm/aia.c | 40 ++++++++++++++++++++++++----------------
> 1 file changed, 24 insertions(+), 16 deletions(-)
>
> diff --git a/arch/riscv/kvm/aia.c b/arch/riscv/kvm/aia.c
> index 5ec503288555..a23729052cfb 100644
> --- a/arch/riscv/kvm/aia.c
> +++ b/arch/riscv/kvm/aia.c
> @@ -23,6 +23,7 @@ struct aia_hgei_control {
> raw_spinlock_t lock;
> unsigned long free_bitmap;
> struct kvm_vcpu *owners[BITS_PER_LONG];
> + unsigned int nr_hgei;
> };
> static DEFINE_PER_CPU(struct aia_hgei_control, aia_hgei);
> static int hgei_parent_irq;
> @@ -452,7 +453,7 @@ void kvm_riscv_aia_free_hgei(int cpu, int hgei)
>
> raw_spin_lock_irqsave(&hgctrl->lock, flags);
>
> - if (hgei > 0 && hgei <= kvm_riscv_aia_nr_hgei) {
> + if (hgei > 0 && hgei <= hgctrl->nr_hgei) {
> if (!(hgctrl->free_bitmap & BIT(hgei))) {
> hgctrl->free_bitmap |= BIT(hgei);
> hgctrl->owners[hgei] = NULL;
> @@ -486,21 +487,8 @@ static irqreturn_t hgei_interrupt(int irq, void *dev_id)
>
> static int aia_hgei_init(void)
> {
> - int cpu, rc;
> + int rc;
> struct irq_domain *domain;
> - struct aia_hgei_control *hgctrl;
> -
> - /* Initialize per-CPU guest external interrupt line management */
> - for_each_possible_cpu(cpu) {
> - hgctrl = per_cpu_ptr(&aia_hgei, cpu);
> - raw_spin_lock_init(&hgctrl->lock);
> - if (kvm_riscv_aia_nr_hgei) {
> - hgctrl->free_bitmap =
> - BIT(kvm_riscv_aia_nr_hgei + 1) - 1;
> - hgctrl->free_bitmap &= ~BIT(0);
> - } else
> - hgctrl->free_bitmap = 0;
> - }
>
> /* Skip SGEI interrupt setup for zero guest external interrupts */
> if (!kvm_riscv_aia_nr_hgei)
> @@ -545,9 +533,29 @@ static void aia_hgei_exit(void)
>
> void kvm_riscv_aia_enable(void)
> {
> + struct aia_hgei_control *hgctrl;
> +
> if (!kvm_riscv_aia_available())
> return;
>
> + hgctrl = this_cpu_ptr(&aia_hgei);
> +
> + /* Figure-out number of bits in HGEIE */
> + csr_write(CSR_HGEIE, -1UL);
> + hgctrl->nr_hgei = fls_long(csr_read(CSR_HGEIE));
> + csr_write(CSR_HGEIE, 0);
> + if (hgctrl->nr_hgei)
> + hgctrl->nr_hgei--;
For completness of this patch, we should also have the following:
if (gc)
hgctrl->nr_hgei= min((ulong)hgctrl->nr_hgei, gc->nr_guest_files);
else
hgctrl->nr_hgei = 0;
Also, over here we should check and update kvm_riscv_aia_nr_hgei
to keep it minimum accross HARTs:
if (hgctrl->nr_hgei && hgctrl->nr_hgei < kvm_riscv_aia_nr_hgei)
kvm_riscv_aia_nr_hgei = hgctrl->nr_hgei;
> +
> + if (hgctrl->nr_hgei) {
> + hgctrl->free_bitmap = BIT(hgctrl->nr_hgei + 1) - 1;
> + hgctrl->free_bitmap &= ~BIT(0);
> + } else {
> + hgctrl->free_bitmap = 0;
> + }
> +
> + raw_spin_lock_init(&hgctrl->lock);
> +
> csr_write(CSR_HVICTL, aia_hvictl_value(false));
> csr_write(CSR_HVIPRIO1, 0x0);
> csr_write(CSR_HVIPRIO2, 0x0);
> @@ -588,7 +596,7 @@ void kvm_riscv_aia_disable(void)
>
> raw_spin_lock_irqsave(&hgctrl->lock, flags);
>
> - for (i = 0; i <= kvm_riscv_aia_nr_hgei; i++) {
> + for (i = 0; i <= hgctrl->nr_hgei; i++) {
> vcpu = hgctrl->owners[i];
> if (!vcpu)
> continue;
> --
> 2.43.0
>
Regards,
Anup
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH V2 2/4] RISC-V: KVM: AIA: Replace global HGEI count with simple enabled bool
2026-04-25 0:59 ` [PATCH V2 2/4] RISC-V: KVM: AIA: Replace global HGEI count with simple enabled bool guoren
@ 2026-05-24 5:24 ` Anup Patel
0 siblings, 0 replies; 13+ messages in thread
From: Anup Patel @ 2026-05-24 5:24 UTC (permalink / raw)
To: guoren
Cc: alex, aou, atish.patra, cp0613, fangyu.yu, gaohan, inochiama,
kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer, pjw, tglx
On Sat, Apr 25, 2026 at 6:29 AM <guoren@kernel.org> wrote:
>
> From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
>
> Now that HGEI line management is fully per-CPU (via struct
> aia_hgei_control::nr_hgei), the global `kvm_riscv_aia_nr_hgei`
> is no longer needed. Replace it with a simple `bool
> kvm_riscv_aia_hgei_enabled` that only indicates whether HGEI
> support is available at all.
As mentioned in PATCH1, this PATCH is not required.
>
> Signed-off-by: Guo Ren (Alibaba DAMO Academy) <guoren@kernel.org>
> ---
> arch/riscv/include/asm/kvm_aia.h | 2 +-
> arch/riscv/kvm/aia.c | 18 ++++++++----------
> arch/riscv/kvm/aia_device.c | 4 ++--
> arch/riscv/kvm/main.c | 3 +--
> 4 files changed, 12 insertions(+), 15 deletions(-)
>
> diff --git a/arch/riscv/include/asm/kvm_aia.h b/arch/riscv/include/asm/kvm_aia.h
> index b04ecdd1a860..e8749ac6bed7 100644
> --- a/arch/riscv/include/asm/kvm_aia.h
> +++ b/arch/riscv/include/asm/kvm_aia.h
> @@ -79,7 +79,7 @@ struct kvm_vcpu_aia {
>
> #define irqchip_in_kernel(k) ((k)->arch.aia.in_kernel)
>
> -extern unsigned int kvm_riscv_aia_nr_hgei;
> +extern bool kvm_riscv_aia_hgei_enabled;
> extern unsigned int kvm_riscv_aia_max_ids;
> DECLARE_STATIC_KEY_FALSE(kvm_riscv_aia_available);
> #define kvm_riscv_aia_available() \
> diff --git a/arch/riscv/kvm/aia.c b/arch/riscv/kvm/aia.c
> index a23729052cfb..70ff1d25dd99 100644
> --- a/arch/riscv/kvm/aia.c
> +++ b/arch/riscv/kvm/aia.c
> @@ -28,7 +28,7 @@ struct aia_hgei_control {
> static DEFINE_PER_CPU(struct aia_hgei_control, aia_hgei);
> static int hgei_parent_irq;
>
> -unsigned int kvm_riscv_aia_nr_hgei;
> +bool kvm_riscv_aia_hgei_enabled;
> unsigned int kvm_riscv_aia_max_ids;
> DEFINE_STATIC_KEY_FALSE(kvm_riscv_aia_available);
>
> @@ -491,7 +491,7 @@ static int aia_hgei_init(void)
> struct irq_domain *domain;
>
> /* Skip SGEI interrupt setup for zero guest external interrupts */
> - if (!kvm_riscv_aia_nr_hgei)
> + if (!kvm_riscv_aia_hgei_enabled)
> goto skip_sgei_interrupt;
>
> /* Find INTC irq domain */
> @@ -524,7 +524,7 @@ static int aia_hgei_init(void)
> static void aia_hgei_exit(void)
> {
> /* Do nothing for zero guest external interrupts */
> - if (!kvm_riscv_aia_nr_hgei)
> + if (!kvm_riscv_aia_hgei_enabled)
> return;
>
> /* Free per-CPU SGEI interrupt */
> @@ -631,6 +631,7 @@ int kvm_riscv_aia_init(void)
> {
> int rc;
> const struct imsic_global_config *gc;
> + unsigned int kvm_riscv_aia_nr_hgei;
>
> if (!riscv_isa_extension_available(NULL, SxAIA))
> return -ENODEV;
> @@ -641,21 +642,18 @@ int kvm_riscv_aia_init(void)
> kvm_riscv_aia_nr_hgei = fls_long(csr_read(CSR_HGEIE));
> csr_write(CSR_HGEIE, 0);
> if (kvm_riscv_aia_nr_hgei)
> - kvm_riscv_aia_nr_hgei--;
> + kvm_riscv_aia_hgei_enabled = true;
>
> /*
> * Number of usable HGEI lines should be minimum of per-HART
> * IMSIC guest files and number of bits in HGEIE
> */
> - if (gc)
> - kvm_riscv_aia_nr_hgei = min((ulong)kvm_riscv_aia_nr_hgei,
> - gc->nr_guest_files);
> - else
> - kvm_riscv_aia_nr_hgei = 0;
> + if (!gc)
> + kvm_riscv_aia_hgei_enabled = 0;
>
> /* Find number of guest MSI IDs */
> kvm_riscv_aia_max_ids = IMSIC_MAX_ID;
> - if (gc && kvm_riscv_aia_nr_hgei)
> + if (gc && kvm_riscv_aia_hgei_enabled)
> kvm_riscv_aia_max_ids = gc->nr_guest_ids + 1;
>
> /* Initialize guest external interrupt line management */
> diff --git a/arch/riscv/kvm/aia_device.c b/arch/riscv/kvm/aia_device.c
> index 3d1e81e2a36b..5b45b1114425 100644
> --- a/arch/riscv/kvm/aia_device.c
> +++ b/arch/riscv/kvm/aia_device.c
> @@ -71,7 +71,7 @@ static int aia_config(struct kvm *kvm, unsigned long type,
> * external interrupts (i.e. non-zero
> * VS-level IMSIC pages).
> */
> - if (!kvm_riscv_aia_nr_hgei)
> + if (!kvm_riscv_aia_hgei_enabled)
> return -EINVAL;
> break;
> default:
> @@ -628,7 +628,7 @@ void kvm_riscv_aia_init_vm(struct kvm *kvm)
> */
>
> /* Initialize default values in AIA global context */
> - aia->mode = (kvm_riscv_aia_nr_hgei) ?
> + aia->mode = (kvm_riscv_aia_hgei_enabled) ?
> KVM_DEV_RISCV_AIA_MODE_AUTO : KVM_DEV_RISCV_AIA_MODE_EMUL;
> aia->nr_ids = kvm_riscv_aia_max_ids - 1;
> aia->nr_sources = 0;
> diff --git a/arch/riscv/kvm/main.c b/arch/riscv/kvm/main.c
> index cb8a65273c1f..bcfa139f4871 100644
> --- a/arch/riscv/kvm/main.c
> +++ b/arch/riscv/kvm/main.c
> @@ -169,8 +169,7 @@ static int __init riscv_kvm_init(void)
> kvm_info("VMID %ld bits available\n", kvm_riscv_gstage_vmid_bits());
>
> if (kvm_riscv_aia_available())
> - kvm_info("AIA available with %d guest external interrupts\n",
> - kvm_riscv_aia_nr_hgei);
> + kvm_info("AIA available with guest external interrupts\n");
>
> kvm_riscv_setup_vendor_features();
>
> --
> 2.43.0
>
Regards,
Anup
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART
2026-04-25 0:59 [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART guoren
` (4 preceding siblings ...)
2026-04-25 1:06 ` Re: [PATCH 3/3] irqchip/riscv-imsic: Remove global nr_guest_files after KVM AIA per-HART conversion guoren
@ 2026-05-24 5:25 ` Anup Patel
5 siblings, 0 replies; 13+ messages in thread
From: Anup Patel @ 2026-05-24 5:25 UTC (permalink / raw)
To: guoren
Cc: alex, aou, atish.patra, cp0613, fangyu.yu, gaohan, inochiama,
kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer, pjw, tglx
On Sat, Apr 25, 2026 at 6:29 AM <guoren@kernel.org> wrote:
>
> From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
>
> This short series converts RISC-V KVM AIA's Hypervisor Guest External
> Interrupt (HGEI) line management from a global "one-size-fits-all"
> model to a fully per-HART (per-CPU) model. It also performs the
> corresponding cleanup in the IMSIC irqchip driver.
>
> The motivation is to properly support heterogeneous RISC-V SoCs
> (big.LITTLE, multi-vendor core mixes) where different HARTs may
> expose different numbers of guest interrupt files / HGEIE bits.
> The old global `kvm_riscv_aia_nr_hgei` and
> `imsic_global_config::nr_guest_files` assumptions are no longer
> tenable and are removed.
>
> After this series, HGEI allocation, freeing, and interrupt delivery
> are completely per-HART, the code is simpler and clearer, and there
> are no remaining global assumptions about guest interrupt file
> counts.
>
> Changelog:
> V2:
> - Add per-HART IMSIC guest files to compute final HGEI count.
> - Add min(local->nr_guest_files, nr_guest_files);
>
> V1:
> https://lore.kernel.org/kvm-riscv/20260421145451.1597930-1-guoren@kernel.org/
>
> Guo Ren (Alibaba DAMO Academy) (4):
> RISC-V: KVM: AIA: Make HGEI number and management fully per-CPU
> RISC-V: KVM: AIA: Replace global HGEI count with simple enabled bool
> irqchip/riscv-imsic: Move nr_guest_files to per-HART local config
> RISC-V: KVM: AIA: Use per-HART IMSIC guest files to compute final HGEI
> count
>
> arch/riscv/include/asm/kvm_aia.h | 2 +-
> arch/riscv/kvm/aia.c | 66 +++++++++++++++----------
> arch/riscv/kvm/aia_device.c | 4 +-
> arch/riscv/kvm/main.c | 3 +-
> drivers/irqchip/irq-riscv-imsic-state.c | 10 ++--
> include/linux/irqchip/riscv-imsic.h | 6 +--
> 6 files changed, 53 insertions(+), 38 deletions(-)
>
> --
> 2.43.0
>
I will send out v3 series to avoid some back-n-forth.
Regards,
Anup
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH V2 1/4] RISC-V: KVM: AIA: Make HGEI number and management fully per-CPU
2026-05-24 5:23 ` Anup Patel
@ 2026-05-26 1:08 ` Guo Ren
0 siblings, 0 replies; 13+ messages in thread
From: Guo Ren @ 2026-05-26 1:08 UTC (permalink / raw)
To: Anup Patel
Cc: alex, aou, atish.patra, cp0613, fangyu.yu, gaohan, inochiama,
kvm-riscv, kvm, linux-kernel, linux-riscv, me, palmer, pjw, tglx
On Sun, May 24, 2026 at 1:23 PM Anup Patel <anup@brainfault.org> wrote:
>
> On Sat, Apr 25, 2026 at 6:29 AM <guoren@kernel.org> wrote:
> >
> > From: "Guo Ren (Alibaba DAMO Academy)" <guoren@kernel.org>
> >
> > Previously the number of Hypervisor Guest External Interrupt (HGEI)
> > lines was stored in a single global variable `kvm_riscv_aia_nr_hgei`
> > and assumed to be the same for all HARTs. This assumption does not
> > hold on heterogeneous RISC-V SoCs where different cores may expose
> > different HGEIE CSR widths.
> >
> > Introduce `nr_hgei` field into the per-CPU `struct aia_hgei_control`
> > and probe the actual supported HGEI count for the current HART in
> > `kvm_riscv_aia_enable()` using the standard RISC-V CSR probe
> > technique:
> >
> > csr_write(CSR_HGEIE, -1UL);
> > nr = fls_long(csr_read(CSR_HGEIE));
> > if (nr)
> > nr--;
> >
> > All HGEI allocation, free and disable paths (`kvm_riscv_aia_free_hgei()`,
> > `kvm_riscv_aia_disable()`, etc.) now use the per-CPU value instead of
> > the global one.
> >
> > The early global `kvm_riscv_aia_nr_hgei` is kept only for deciding
> > whether SGEI interrupt registration is needed; the real per-HART
> > initialization of lock and free_bitmap is moved to enable time.
>
> We should keep the `kvm_riscv_aia_nr_hgei` to imply two things:
> 1) Minimum number of HGEI lines available across all HARTs
> 2) Non-zero kvm_riscv_aia_nr_hgei means HGEI is enabled
>
> The PATCH2 is redundant and must be droped. I will take care
> care of this at the time of merging.
Okay.
>
> >
> > This makes KVM AIA robust on big.LITTLE-style and multi-vendor
> > asymmetric platforms.
> >
> > Signed-off-by: Guo Ren (Alibaba DAMO Academy) <guoren@kernel.org>
> > ---
> > arch/riscv/kvm/aia.c | 40 ++++++++++++++++++++++++----------------
> > 1 file changed, 24 insertions(+), 16 deletions(-)
> >
> > diff --git a/arch/riscv/kvm/aia.c b/arch/riscv/kvm/aia.c
> > index 5ec503288555..a23729052cfb 100644
> > --- a/arch/riscv/kvm/aia.c
> > +++ b/arch/riscv/kvm/aia.c
> > @@ -23,6 +23,7 @@ struct aia_hgei_control {
> > raw_spinlock_t lock;
> > unsigned long free_bitmap;
> > struct kvm_vcpu *owners[BITS_PER_LONG];
> > + unsigned int nr_hgei;
> > };
> > static DEFINE_PER_CPU(struct aia_hgei_control, aia_hgei);
> > static int hgei_parent_irq;
> > @@ -452,7 +453,7 @@ void kvm_riscv_aia_free_hgei(int cpu, int hgei)
> >
> > raw_spin_lock_irqsave(&hgctrl->lock, flags);
> >
> > - if (hgei > 0 && hgei <= kvm_riscv_aia_nr_hgei) {
> > + if (hgei > 0 && hgei <= hgctrl->nr_hgei) {
> > if (!(hgctrl->free_bitmap & BIT(hgei))) {
> > hgctrl->free_bitmap |= BIT(hgei);
> > hgctrl->owners[hgei] = NULL;
> > @@ -486,21 +487,8 @@ static irqreturn_t hgei_interrupt(int irq, void *dev_id)
> >
> > static int aia_hgei_init(void)
> > {
> > - int cpu, rc;
> > + int rc;
> > struct irq_domain *domain;
> > - struct aia_hgei_control *hgctrl;
> > -
> > - /* Initialize per-CPU guest external interrupt line management */
> > - for_each_possible_cpu(cpu) {
> > - hgctrl = per_cpu_ptr(&aia_hgei, cpu);
> > - raw_spin_lock_init(&hgctrl->lock);
> > - if (kvm_riscv_aia_nr_hgei) {
> > - hgctrl->free_bitmap =
> > - BIT(kvm_riscv_aia_nr_hgei + 1) - 1;
> > - hgctrl->free_bitmap &= ~BIT(0);
> > - } else
> > - hgctrl->free_bitmap = 0;
> > - }
> >
> > /* Skip SGEI interrupt setup for zero guest external interrupts */
> > if (!kvm_riscv_aia_nr_hgei)
> > @@ -545,9 +533,29 @@ static void aia_hgei_exit(void)
> >
> > void kvm_riscv_aia_enable(void)
> > {
> > + struct aia_hgei_control *hgctrl;
> > +
> > if (!kvm_riscv_aia_available())
> > return;
> >
> > + hgctrl = this_cpu_ptr(&aia_hgei);
> > +
> > + /* Figure-out number of bits in HGEIE */
> > + csr_write(CSR_HGEIE, -1UL);
> > + hgctrl->nr_hgei = fls_long(csr_read(CSR_HGEIE));
> > + csr_write(CSR_HGEIE, 0);
> > + if (hgctrl->nr_hgei)
> > + hgctrl->nr_hgei--;
>
> For completness of this patch, we should also have the following:
>
> if (gc)
> hgctrl->nr_hgei= min((ulong)hgctrl->nr_hgei, gc->nr_guest_files);
Thanks for the review!
On keeping kvm_riscv_aia_nr_hgei as the minimum across all HARTs:
I agree to keep kvm_riscv_aia_nr_hgei as a non-zero indicator for HGEI
enablement. However, I have a concern about making it track the
per-HART minimum. The purpose of this patch is precisely to let each
HART use its own nr_hgei independently, so heterogeneous HARTs with
more HGEI lines are not artificially limited by weaker ones.
Collapsing that back into a global minimum would partially defeat the
goal.
ref: global->nr_guest_files = min(global->nr_guest_files,
local->nr_guest_files);
> else
> hgctrl->nr_hgei = 0;
>
> Also, over here we should check and update kvm_riscv_aia_nr_hgei
> to keep it minimum accross HARTs:
>
> if (hgctrl->nr_hgei && hgctrl->nr_hgei < kvm_riscv_aia_nr_hgei)
> kvm_riscv_aia_nr_hgei = hgctrl->nr_hgei;
>
> > +
> > + if (hgctrl->nr_hgei) {
> > + hgctrl->free_bitmap = BIT(hgctrl->nr_hgei + 1) - 1;
> > + hgctrl->free_bitmap &= ~BIT(0);
> > + } else {
> > + hgctrl->free_bitmap = 0;
> > + }
> > +
> > + raw_spin_lock_init(&hgctrl->lock);
> > +
> > csr_write(CSR_HVICTL, aia_hvictl_value(false));
> > csr_write(CSR_HVIPRIO1, 0x0);
> > csr_write(CSR_HVIPRIO2, 0x0);
> > @@ -588,7 +596,7 @@ void kvm_riscv_aia_disable(void)
> >
> > raw_spin_lock_irqsave(&hgctrl->lock, flags);
> >
> > - for (i = 0; i <= kvm_riscv_aia_nr_hgei; i++) {
> > + for (i = 0; i <= hgctrl->nr_hgei; i++) {
> > vcpu = hgctrl->owners[i];
> > if (!vcpu)
> > continue;
> > --
> > 2.43.0
> >
>
> Regards,
> Anup
--
Best Regards
Guo Ren
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
^ permalink raw reply [flat|nested] 13+ messages in thread
end of thread, other threads:[~2026-05-26 1:08 UTC | newest]
Thread overview: 13+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-04-25 0:59 [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART guoren
2026-04-25 0:59 ` [PATCH V2 1/4] RISC-V: KVM: AIA: Make HGEI number and management fully per-CPU guoren
2026-05-24 5:23 ` Anup Patel
2026-05-26 1:08 ` Guo Ren
2026-04-25 0:59 ` [PATCH V2 2/4] RISC-V: KVM: AIA: Replace global HGEI count with simple enabled bool guoren
2026-05-24 5:24 ` Anup Patel
2026-04-25 0:59 ` [PATCH V2 3/4] irqchip/riscv-imsic: Move nr_guest_files to per-HART local config guoren
2026-05-05 20:12 ` Thomas Gleixner
2026-05-07 10:04 ` Guo Ren
2026-05-07 12:01 ` Anup Patel
2026-04-25 0:59 ` [PATCH V2 4/4] RISC-V: KVM: AIA: Use per-HART IMSIC guest files to compute final HGEI count guoren
2026-04-25 1:06 ` Re: [PATCH 3/3] irqchip/riscv-imsic: Remove global nr_guest_files after KVM AIA per-HART conversion guoren
2026-05-24 5:25 ` [PATCH V2 0/4] RISC-V: KVM: AIA: Convert HGEI management to fully per-HART Anup Patel
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox