* [RFC PATCH 0/2] RISC-V: KVM: Pointer Masking Support
@ 2025-01-11 0:46 Samuel Holland
2025-01-11 0:46 ` [RFC PATCH 1/2] RISC-V: KVM: Fix inclusion of Smnpm in the guest ISA bitmap Samuel Holland
` (2 more replies)
0 siblings, 3 replies; 4+ messages in thread
From: Samuel Holland @ 2025-01-11 0:46 UTC (permalink / raw)
To: Anup Patel, Atish Patra, kvm-riscv, linux-riscv
Cc: Samuel Holland, Albert Ou, Palmer Dabbelt, Paul Walmsley, kvm,
linux-kernel
This series adds support for pointer masking in VS-mode inside KVM
guests using the SBI FWFT extension. This series applies on top of
Clément's "riscv: add SBI FWFT misaligned exception delegation support"
series[1], which adds the necessary infrastructure.
[1]: https://lore.kernel.org/linux-riscv/20250106154847.1100344-1-cleger@rivosinc.com/
Samuel Holland (2):
RISC-V: KVM: Fix inclusion of Smnpm in the guest ISA bitmap
RISC-V: KVM: Add support for SBI_FWFT_POINTER_MASKING_PMLEN
arch/riscv/include/asm/kvm_vcpu_sbi_fwft.h | 2 +
arch/riscv/kvm/vcpu_onereg.c | 84 ++++++++++++++--------
arch/riscv/kvm/vcpu_sbi_fwft.c | 70 +++++++++++++++++-
3 files changed, 124 insertions(+), 32 deletions(-)
--
2.47.0
--
kvm-riscv mailing list
kvm-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/kvm-riscv
^ permalink raw reply [flat|nested] 4+ messages in thread
* [RFC PATCH 1/2] RISC-V: KVM: Fix inclusion of Smnpm in the guest ISA bitmap
2025-01-11 0:46 [RFC PATCH 0/2] RISC-V: KVM: Pointer Masking Support Samuel Holland
@ 2025-01-11 0:46 ` Samuel Holland
2025-01-11 0:46 ` [RFC PATCH 2/2] RISC-V: KVM: Add support for SBI_FWFT_POINTER_MASKING_PMLEN Samuel Holland
2025-07-16 12:24 ` [RFC PATCH 0/2] RISC-V: KVM: Pointer Masking Support Anup Patel
2 siblings, 0 replies; 4+ messages in thread
From: Samuel Holland @ 2025-01-11 0:46 UTC (permalink / raw)
To: Anup Patel, Atish Patra, kvm-riscv, linux-riscv
Cc: Samuel Holland, Albert Ou, Palmer Dabbelt, Paul Walmsley, kvm,
linux-kernel
The Smnpm extension requires special handling because the guest ISA
extension maps to a different extension (Ssnpm) on the host side.
commit 1851e7836212 ("RISC-V: KVM: Allow Smnpm and Ssnpm extensions for
guests") missed that the vcpu->arch.isa bit is based only on the host
extension, so currently both KVM_RISCV_ISA_EXT_{SMNPM,SSNPM} map to
vcpu->arch.isa[RISCV_ISA_EXT_SSNPM]. This does not cause any problems
for the guest, because both extensions are force-enabled anyway when the
host supports Ssnpm, but prevents checking for (guest) Smnpm in the SBI
FWFT logic.
Redefine kvm_isa_ext_arr to look up the guest extension, since only the
guest -> host mapping is unambiguous. Factor out the logic for checking
for host support of an extension, so this special case only needs to be
handled in one place, and be explicit about which variables hold a host
vs a guest ISA extension.
Fixes: 1851e7836212 ("RISC-V: KVM: Allow Smnpm and Ssnpm extensions for guests")
Signed-off-by: Samuel Holland <samuel.holland@sifive.com>
---
arch/riscv/kvm/vcpu_onereg.c | 83 +++++++++++++++++++++++-------------
1 file changed, 53 insertions(+), 30 deletions(-)
diff --git a/arch/riscv/kvm/vcpu_onereg.c b/arch/riscv/kvm/vcpu_onereg.c
index 753f66c8b70a..93115abca3b8 100644
--- a/arch/riscv/kvm/vcpu_onereg.c
+++ b/arch/riscv/kvm/vcpu_onereg.c
@@ -23,7 +23,7 @@
#define KVM_ISA_EXT_ARR(ext) \
[KVM_RISCV_ISA_EXT_##ext] = RISCV_ISA_EXT_##ext
-/* Mapping between KVM ISA Extension ID & Host ISA extension ID */
+/* Mapping between KVM ISA Extension ID & guest ISA extension ID */
static const unsigned long kvm_isa_ext_arr[] = {
/* Single letter extensions (alphabetically sorted) */
[KVM_RISCV_ISA_EXT_A] = RISCV_ISA_EXT_a,
@@ -35,7 +35,7 @@ static const unsigned long kvm_isa_ext_arr[] = {
[KVM_RISCV_ISA_EXT_M] = RISCV_ISA_EXT_m,
[KVM_RISCV_ISA_EXT_V] = RISCV_ISA_EXT_v,
/* Multi letter extensions (alphabetically sorted) */
- [KVM_RISCV_ISA_EXT_SMNPM] = RISCV_ISA_EXT_SSNPM,
+ KVM_ISA_EXT_ARR(SMNPM),
KVM_ISA_EXT_ARR(SMSTATEEN),
KVM_ISA_EXT_ARR(SSAIA),
KVM_ISA_EXT_ARR(SSCOFPMF),
@@ -107,6 +107,36 @@ static unsigned long kvm_riscv_vcpu_base2isa_ext(unsigned long base_ext)
return KVM_RISCV_ISA_EXT_MAX;
}
+static int kvm_riscv_vcpu_isa_check_host(unsigned long kvm_ext, unsigned long *guest_ext)
+{
+ unsigned long host_ext;
+
+ if (kvm_ext >= KVM_RISCV_ISA_EXT_MAX ||
+ kvm_ext >= ARRAY_SIZE(kvm_isa_ext_arr))
+ return -ENOENT;
+
+ *guest_ext = kvm_isa_ext_arr[kvm_ext];
+ switch (*guest_ext) {
+ case RISCV_ISA_EXT_SMNPM:
+ /*
+ * Pointer masking effective in (H)S-mode is provided by the
+ * Smnpm extension, so that extension is reported to the guest,
+ * even though the CSR bits for configuring VS-mode pointer
+ * masking on the host side are part of the Ssnpm extension.
+ */
+ host_ext = RISCV_ISA_EXT_SSNPM;
+ break;
+ default:
+ host_ext = *guest_ext;
+ break;
+ }
+
+ if (!__riscv_isa_extension_available(NULL, host_ext))
+ return -ENOENT;
+
+ return 0;
+}
+
static bool kvm_riscv_vcpu_isa_enable_allowed(unsigned long ext)
{
switch (ext) {
@@ -209,13 +239,13 @@ static bool kvm_riscv_vcpu_isa_disable_allowed(unsigned long ext)
void kvm_riscv_vcpu_setup_isa(struct kvm_vcpu *vcpu)
{
- unsigned long host_isa, i;
+ unsigned long guest_ext, i;
for (i = 0; i < ARRAY_SIZE(kvm_isa_ext_arr); i++) {
- host_isa = kvm_isa_ext_arr[i];
- if (__riscv_isa_extension_available(NULL, host_isa) &&
- kvm_riscv_vcpu_isa_enable_allowed(i))
- set_bit(host_isa, vcpu->arch.isa);
+ if (kvm_riscv_vcpu_isa_check_host(i, &guest_ext))
+ continue;
+ if (kvm_riscv_vcpu_isa_enable_allowed(i))
+ set_bit(guest_ext, vcpu->arch.isa);
}
}
@@ -597,18 +627,15 @@ static int riscv_vcpu_get_isa_ext_single(struct kvm_vcpu *vcpu,
unsigned long reg_num,
unsigned long *reg_val)
{
- unsigned long host_isa_ext;
-
- if (reg_num >= KVM_RISCV_ISA_EXT_MAX ||
- reg_num >= ARRAY_SIZE(kvm_isa_ext_arr))
- return -ENOENT;
+ unsigned long guest_ext;
+ int ret;
- host_isa_ext = kvm_isa_ext_arr[reg_num];
- if (!__riscv_isa_extension_available(NULL, host_isa_ext))
- return -ENOENT;
+ ret = kvm_riscv_vcpu_isa_check_host(reg_num, &guest_ext);
+ if (ret)
+ return ret;
*reg_val = 0;
- if (__riscv_isa_extension_available(vcpu->arch.isa, host_isa_ext))
+ if (__riscv_isa_extension_available(vcpu->arch.isa, guest_ext))
*reg_val = 1; /* Mark the given extension as available */
return 0;
@@ -618,17 +645,14 @@ static int riscv_vcpu_set_isa_ext_single(struct kvm_vcpu *vcpu,
unsigned long reg_num,
unsigned long reg_val)
{
- unsigned long host_isa_ext;
-
- if (reg_num >= KVM_RISCV_ISA_EXT_MAX ||
- reg_num >= ARRAY_SIZE(kvm_isa_ext_arr))
- return -ENOENT;
+ unsigned long guest_ext;
+ int ret;
- host_isa_ext = kvm_isa_ext_arr[reg_num];
- if (!__riscv_isa_extension_available(NULL, host_isa_ext))
- return -ENOENT;
+ ret = kvm_riscv_vcpu_isa_check_host(reg_num, &guest_ext);
+ if (ret)
+ return ret;
- if (reg_val == test_bit(host_isa_ext, vcpu->arch.isa))
+ if (reg_val == test_bit(guest_ext, vcpu->arch.isa))
return 0;
if (!vcpu->arch.ran_atleast_once) {
@@ -638,10 +662,10 @@ static int riscv_vcpu_set_isa_ext_single(struct kvm_vcpu *vcpu,
*/
if (reg_val == 1 &&
kvm_riscv_vcpu_isa_enable_allowed(reg_num))
- set_bit(host_isa_ext, vcpu->arch.isa);
+ set_bit(guest_ext, vcpu->arch.isa);
else if (!reg_val &&
kvm_riscv_vcpu_isa_disable_allowed(reg_num))
- clear_bit(host_isa_ext, vcpu->arch.isa);
+ clear_bit(guest_ext, vcpu->arch.isa);
else
return -EINVAL;
kvm_riscv_vcpu_fp_reset(vcpu);
@@ -999,16 +1023,15 @@ static int copy_fp_d_reg_indices(const struct kvm_vcpu *vcpu,
static int copy_isa_ext_reg_indices(const struct kvm_vcpu *vcpu,
u64 __user *uindices)
{
+ unsigned long guest_ext;
unsigned int n = 0;
- unsigned long isa_ext;
for (int i = 0; i < KVM_RISCV_ISA_EXT_MAX; i++) {
u64 size = IS_ENABLED(CONFIG_32BIT) ?
KVM_REG_SIZE_U32 : KVM_REG_SIZE_U64;
u64 reg = KVM_REG_RISCV | size | KVM_REG_RISCV_ISA_EXT | i;
- isa_ext = kvm_isa_ext_arr[i];
- if (!__riscv_isa_extension_available(NULL, isa_ext))
+ if (kvm_riscv_vcpu_isa_check_host(i, &guest_ext))
continue;
if (uindices) {
--
2.47.0
--
kvm-riscv mailing list
kvm-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/kvm-riscv
^ permalink raw reply related [flat|nested] 4+ messages in thread
* [RFC PATCH 2/2] RISC-V: KVM: Add support for SBI_FWFT_POINTER_MASKING_PMLEN
2025-01-11 0:46 [RFC PATCH 0/2] RISC-V: KVM: Pointer Masking Support Samuel Holland
2025-01-11 0:46 ` [RFC PATCH 1/2] RISC-V: KVM: Fix inclusion of Smnpm in the guest ISA bitmap Samuel Holland
@ 2025-01-11 0:46 ` Samuel Holland
2025-07-16 12:24 ` [RFC PATCH 0/2] RISC-V: KVM: Pointer Masking Support Anup Patel
2 siblings, 0 replies; 4+ messages in thread
From: Samuel Holland @ 2025-01-11 0:46 UTC (permalink / raw)
To: Anup Patel, Atish Patra, kvm-riscv, linux-riscv
Cc: Samuel Holland, Albert Ou, Palmer Dabbelt, Paul Walmsley, kvm,
linux-kernel
Pointer masking is controlled through a WARL field in henvcfg. Expose
the feature only if at least one PMLEN value is supported for VS-mode.
Allow the VMM to block access to the feature by disabling the Smnpm ISA
extension in the guest.
Signed-off-by: Samuel Holland <samuel.holland@sifive.com>
---
arch/riscv/include/asm/kvm_vcpu_sbi_fwft.h | 2 +
arch/riscv/kvm/vcpu_onereg.c | 1 -
arch/riscv/kvm/vcpu_sbi_fwft.c | 70 +++++++++++++++++++++-
3 files changed, 71 insertions(+), 2 deletions(-)
diff --git a/arch/riscv/include/asm/kvm_vcpu_sbi_fwft.h b/arch/riscv/include/asm/kvm_vcpu_sbi_fwft.h
index 5782517f6e08..5176344d9162 100644
--- a/arch/riscv/include/asm/kvm_vcpu_sbi_fwft.h
+++ b/arch/riscv/include/asm/kvm_vcpu_sbi_fwft.h
@@ -30,6 +30,8 @@ struct kvm_sbi_fwft_config {
/* FWFT data structure per vcpu */
struct kvm_sbi_fwft {
struct kvm_sbi_fwft_config *configs;
+ bool have_vs_pmlen_7;
+ bool have_vs_pmlen_16;
};
#define vcpu_to_fwft(vcpu) (&(vcpu)->arch.fwft_context)
diff --git a/arch/riscv/kvm/vcpu_onereg.c b/arch/riscv/kvm/vcpu_onereg.c
index 93115abca3b8..1d2033b33e6d 100644
--- a/arch/riscv/kvm/vcpu_onereg.c
+++ b/arch/riscv/kvm/vcpu_onereg.c
@@ -168,7 +168,6 @@ static bool kvm_riscv_vcpu_isa_disable_allowed(unsigned long ext)
case KVM_RISCV_ISA_EXT_C:
case KVM_RISCV_ISA_EXT_I:
case KVM_RISCV_ISA_EXT_M:
- case KVM_RISCV_ISA_EXT_SMNPM:
/* There is not architectural config bit to disable sscofpmf completely */
case KVM_RISCV_ISA_EXT_SSCOFPMF:
case KVM_RISCV_ISA_EXT_SSNPM:
diff --git a/arch/riscv/kvm/vcpu_sbi_fwft.c b/arch/riscv/kvm/vcpu_sbi_fwft.c
index 1e85ff6666af..6e8f818fd6f5 100644
--- a/arch/riscv/kvm/vcpu_sbi_fwft.c
+++ b/arch/riscv/kvm/vcpu_sbi_fwft.c
@@ -68,13 +68,81 @@ static int kvm_sbi_fwft_get_misaligned_delegation(struct kvm_vcpu *vcpu,
return SBI_SUCCESS;
}
+static bool try_to_set_pmm(unsigned long value)
+{
+ csr_set(CSR_HENVCFG, value);
+ return (csr_read_clear(CSR_HENVCFG, ENVCFG_PMM) & ENVCFG_PMM) == value;
+}
+
+static bool kvm_sbi_fwft_pointer_masking_pmlen_supported(struct kvm_vcpu *vcpu)
+{
+ struct kvm_sbi_fwft *fwft = vcpu_to_fwft(vcpu);
+
+ if (!riscv_isa_extension_available(vcpu->arch.isa, SMNPM))
+ return false;
+
+ fwft->have_vs_pmlen_7 = try_to_set_pmm(ENVCFG_PMM_PMLEN_7);
+ fwft->have_vs_pmlen_16 = try_to_set_pmm(ENVCFG_PMM_PMLEN_16);
+
+ return fwft->have_vs_pmlen_7 || fwft->have_vs_pmlen_16;
+}
+
+static int kvm_sbi_fwft_set_pointer_masking_pmlen(struct kvm_vcpu *vcpu,
+ struct kvm_sbi_fwft_config *conf,
+ unsigned long value)
+{
+ struct kvm_sbi_fwft *fwft = vcpu_to_fwft(vcpu);
+ unsigned long pmm;
+
+ if (value == 0)
+ pmm = ENVCFG_PMM_PMLEN_0;
+ else if (value <= 7 && fwft->have_vs_pmlen_7)
+ pmm = ENVCFG_PMM_PMLEN_7;
+ else if (value <= 16 && fwft->have_vs_pmlen_16)
+ pmm = ENVCFG_PMM_PMLEN_16;
+ else
+ return SBI_ERR_INVALID_PARAM;
+
+ vcpu->arch.cfg.henvcfg &= ~ENVCFG_PMM;
+ vcpu->arch.cfg.henvcfg |= pmm;
+
+ return SBI_SUCCESS;
+}
+
+static int kvm_sbi_fwft_get_pointer_masking_pmlen(struct kvm_vcpu *vcpu,
+ struct kvm_sbi_fwft_config *conf,
+ unsigned long *value)
+{
+ switch (vcpu->arch.cfg.henvcfg & ENVCFG_PMM) {
+ case ENVCFG_PMM_PMLEN_0:
+ *value = 0;
+ break;
+ case ENVCFG_PMM_PMLEN_7:
+ *value = 7;
+ break;
+ case ENVCFG_PMM_PMLEN_16:
+ *value = 16;
+ break;
+ default:
+ return SBI_ERR_FAILURE;
+ }
+
+ return SBI_SUCCESS;
+}
+
static const struct kvm_sbi_fwft_feature features[] = {
{
.id = SBI_FWFT_MISALIGNED_EXC_DELEG,
.supported = kvm_sbi_fwft_misaligned_delegation_supported,
.set = kvm_sbi_fwft_set_misaligned_delegation,
.get = kvm_sbi_fwft_get_misaligned_delegation,
- }
+ },
+ {
+ .id = SBI_FWFT_POINTER_MASKING_PMLEN,
+ .supported = kvm_sbi_fwft_pointer_masking_pmlen_supported,
+ .set = kvm_sbi_fwft_set_pointer_masking_pmlen,
+ .get = kvm_sbi_fwft_get_pointer_masking_pmlen,
+ },
};
static struct kvm_sbi_fwft_config *
--
2.47.0
--
kvm-riscv mailing list
kvm-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/kvm-riscv
^ permalink raw reply related [flat|nested] 4+ messages in thread
* Re: [RFC PATCH 0/2] RISC-V: KVM: Pointer Masking Support
2025-01-11 0:46 [RFC PATCH 0/2] RISC-V: KVM: Pointer Masking Support Samuel Holland
2025-01-11 0:46 ` [RFC PATCH 1/2] RISC-V: KVM: Fix inclusion of Smnpm in the guest ISA bitmap Samuel Holland
2025-01-11 0:46 ` [RFC PATCH 2/2] RISC-V: KVM: Add support for SBI_FWFT_POINTER_MASKING_PMLEN Samuel Holland
@ 2025-07-16 12:24 ` Anup Patel
2 siblings, 0 replies; 4+ messages in thread
From: Anup Patel @ 2025-07-16 12:24 UTC (permalink / raw)
To: Samuel Holland
Cc: Atish Patra, kvm-riscv, linux-riscv, Albert Ou, Palmer Dabbelt,
Paul Walmsley, kvm, linux-kernel
On Sat, Jan 11, 2025 at 6:17 AM Samuel Holland
<samuel.holland@sifive.com> wrote:
>
> This series adds support for pointer masking in VS-mode inside KVM
> guests using the SBI FWFT extension. This series applies on top of
> Clément's "riscv: add SBI FWFT misaligned exception delegation support"
> series[1], which adds the necessary infrastructure.
>
> [1]: https://lore.kernel.org/linux-riscv/20250106154847.1100344-1-cleger@rivosinc.com/
>
>
> Samuel Holland (2):
> RISC-V: KVM: Fix inclusion of Smnpm in the guest ISA bitmap
> RISC-V: KVM: Add support for SBI_FWFT_POINTER_MASKING_PMLEN
LGTM.
Reviewed-by: Anup Patel <anup@brainfault.org>
Rebased and queued it for Linux-6.17
Thanks,
Anup
--
kvm-riscv mailing list
kvm-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/kvm-riscv
^ permalink raw reply [flat|nested] 4+ messages in thread
end of thread, other threads:[~2025-07-16 12:24 UTC | newest]
Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-01-11 0:46 [RFC PATCH 0/2] RISC-V: KVM: Pointer Masking Support Samuel Holland
2025-01-11 0:46 ` [RFC PATCH 1/2] RISC-V: KVM: Fix inclusion of Smnpm in the guest ISA bitmap Samuel Holland
2025-01-11 0:46 ` [RFC PATCH 2/2] RISC-V: KVM: Add support for SBI_FWFT_POINTER_MASKING_PMLEN Samuel Holland
2025-07-16 12:24 ` [RFC PATCH 0/2] RISC-V: KVM: Pointer Masking Support Anup Patel
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).