[PATCH v3 2/2] RISC-V: KVM: Introduce make_xfence_request_nodata for FENCE.I requests
From: Wang Yechao
Date: Fri Jul 31 2026 - 05:43:23 EST
FENCE.I does not need hfence data, but it currently goes through the
generic make_xfence_request() path with NULL data, incurring unnecessary
per-VCPU checks.
Split out a separate make_xfence_request_nodata() function to handle
FENCE.I directly, and move the data validity check to the top of the
generic function to avoid redundant checks.
Signed-off-by: Wang Yechao <wang.yechao255@xxxxxxxxxx>
---
arch/riscv/kvm/tlb.c | 34 +++++++++++++++++++++++++++-------
1 file changed, 27 insertions(+), 7 deletions(-)
diff --git a/arch/riscv/kvm/tlb.c b/arch/riscv/kvm/tlb.c
index c54522decaa64..fd445e9fa3f94 100644
--- a/arch/riscv/kvm/tlb.c
+++ b/arch/riscv/kvm/tlb.c
@@ -325,6 +325,29 @@ void kvm_riscv_hfence_process(struct kvm_vcpu *vcpu)
}
}
+static void make_xfence_request_nodata(struct kvm *kvm, unsigned long hbase,
+ unsigned long hmask, unsigned int req)
+{
+ unsigned long i;
+ struct kvm_vcpu *vcpu;
+ DECLARE_BITMAP(vcpu_mask, KVM_MAX_VCPUS);
+
+ bitmap_zero(vcpu_mask, KVM_MAX_VCPUS);
+ kvm_for_each_vcpu(i, vcpu, kvm) {
+ if (hbase != -1UL) {
+ if (vcpu->vcpu_id < hbase ||
+ vcpu->vcpu_id >= hbase + BITS_PER_LONG)
+ continue;
+ if (!(hmask & (1UL << (vcpu->vcpu_id - hbase))))
+ continue;
+ }
+
+ bitmap_set(vcpu_mask, i, 1);
+ }
+
+ kvm_make_vcpus_request_mask(kvm, req, vcpu_mask);
+}
+
static void make_xfence_request(struct kvm *kvm,
unsigned long hbase, unsigned long hmask,
unsigned int req, unsigned int fallback_req,
@@ -335,6 +358,9 @@ static void make_xfence_request(struct kvm *kvm,
DECLARE_BITMAP(req_vcpu_mask, KVM_MAX_VCPUS);
DECLARE_BITMAP(fallback_req_vcpu_mask, KVM_MAX_VCPUS);
+ if (!data || !data->type)
+ return;
+
bitmap_zero(req_vcpu_mask, KVM_MAX_VCPUS);
bitmap_zero(fallback_req_vcpu_mask, KVM_MAX_VCPUS);
kvm_for_each_vcpu(i, vcpu, kvm) {
@@ -346,11 +372,6 @@ static void make_xfence_request(struct kvm *kvm,
continue;
}
- if (!data || !data->type) {
- bitmap_set(req_vcpu_mask, i, 1);
- continue;
- }
-
/*
* Enqueue hfence data to VCPU hfence queue. If we don't
* have space in the VCPU hfence queue then fallback to
@@ -369,8 +390,7 @@ static void make_xfence_request(struct kvm *kvm,
void kvm_riscv_fence_i(struct kvm *kvm,
unsigned long hbase, unsigned long hmask)
{
- make_xfence_request(kvm, hbase, hmask, KVM_REQ_FENCE_I,
- KVM_REQ_FENCE_I, NULL);
+ make_xfence_request_nodata(kvm, hbase, hmask, KVM_REQ_FENCE_I);
}
void kvm_riscv_hfence_gvma_vmid_gpa(struct kvm *kvm,
--
2.39.3