[clang] [llvm] [RISCV]Support Sspmp, Sspmpen and Smpmpdeleg Extensions (PR #207696)
Liao Chunyu via cfe-commits
cfe-commits at lists.llvm.org
Mon Jul 6 03:30:03 PDT 2026
https://github.com/ChunyuLiao created https://github.com/llvm/llvm-project/pull/207696
Spec states: https://riscv.atlassian.net/browse/RVS-921
>From e01d3dd4470ef53435bc8e4ed4909f937fac4e81 Mon Sep 17 00:00:00 2001
From: Liao Chunyu <chunyu at iscas.ac.cn>
Date: Mon, 6 Jul 2026 10:00:47 +0000
Subject: [PATCH] [RISCV]Support Sspmp, Sspmpen and Smpmpdeleg Extensions
---
.../Driver/print-supported-extensions-riscv.c | 3 ++
.../test/Preprocessor/riscv-target-features.c | 33 ++++++++++++
llvm/docs/RISCVUsage.rst | 3 ++
llvm/lib/Target/RISCV/RISCVFeatures.td | 10 ++++
llvm/lib/Target/RISCV/RISCVSystemOperands.td | 4 ++
llvm/test/CodeGen/RISCV/features-info.ll | 3 ++
llvm/test/MC/RISCV/attribute-arch.s | 9 ++++
llvm/test/MC/RISCV/spmp-csr-names.s | 50 +++++++++++++++++++
.../TargetParser/RISCVISAInfoTest.cpp | 3 ++
9 files changed, 118 insertions(+)
create mode 100644 llvm/test/MC/RISCV/spmp-csr-names.s
diff --git a/clang/test/Driver/print-supported-extensions-riscv.c b/clang/test/Driver/print-supported-extensions-riscv.c
index 34c651891538d..f56887cc449cf 100644
--- a/clang/test/Driver/print-supported-extensions-riscv.c
+++ b/clang/test/Driver/print-supported-extensions-riscv.c
@@ -135,6 +135,7 @@
// CHECK-NEXT: smepmp 1.0 'Smepmp' (Enhanced Physical Memory Protection)
// CHECK-NEXT: smmpm 1.0 'Smmpm' (Machine-level Pointer Masking for M-mode)
// CHECK-NEXT: smnpm 1.0 'Smnpm' (Machine-level Pointer Masking for next lower privilege mode)
+// CHECK-NEXT: smpmpdeleg 1.0 'Smpmpdeleg' (Sharing Hardware Resources between PMP and SPMP)
// CHECK-NEXT: smrnmi 1.0 'Smrnmi' (Resumable Non-Maskable Interrupts)
// CHECK-NEXT: smstateen 1.0 'Smstateen' (Machine-mode view of the state-enable extension)
// CHECK-NEXT: ssaia 1.0 'Ssaia' (Advanced Interrupt Architecture Supervisor Level)
@@ -147,6 +148,8 @@
// CHECK-NEXT: ssdbltrp 1.0 'Ssdbltrp' (Double Trap Supervisor Level)
// CHECK-NEXT: ssnpm 1.0 'Ssnpm' (Supervisor-level Pointer Masking for next lower privilege mode)
// CHECK-NEXT: sspm 1.0 'Sspm' (Indicates Supervisor-mode Pointer Masking)
+// CHECK-NEXT: sspmp 1.0 'Sspmp' (S-level Physical Memory Protection (SPMP))
+// CHECK-NEXT: sspmpen 1.0 'Sspmpen' (Optimizing Context Switching of SPMP Entries)
// CHECK-NEXT: ssqosid 1.0 'Ssqosid' (Quality-of-Service (QoS) Identifiers)
// CHECK-NEXT: ssstateen 1.0 'Ssstateen' (Supervisor-mode view of the state-enable extension)
// CHECK-NEXT: ssstrict 1.0 'Ssstrict' (No non-conforming extensions are present)
diff --git a/clang/test/Preprocessor/riscv-target-features.c b/clang/test/Preprocessor/riscv-target-features.c
index 28031814da16a..7762a217f906a 100644
--- a/clang/test/Preprocessor/riscv-target-features.c
+++ b/clang/test/Preprocessor/riscv-target-features.c
@@ -38,6 +38,7 @@
// CHECK-NOT: __riscv_smctr{{.*$}}
// CHECK-NOT: __riscv_smdbltrp {{.*$}}
// CHECK-NOT: __riscv_smepmp {{.*$}}
+// CHECK-NOT: __riscv_smpmpdeleg {{.*$}}
// CHECK-NOT: __riscv_smmpm{{.*$}}
// CHECK-NOT: __riscv_smnpm{{.*$}}
// CHECK-NOT: __riscv_smpmpmt {{.*$}}
@@ -53,6 +54,8 @@
// CHECK-NOT: __riscv_ssdbltrp {{.*$}}
// CHECK-NOT: __riscv_ssnpm{{.*$}}
// CHECK-NOT: __riscv_sspm{{.*$}}
+// CHECK-NOT: __riscv_sspmp {{.*$}}
+// CHECK-NOT: __riscv_sspmpen {{.*$}}
// CHECK-NOT: __riscv_ssqosid{{.*$}}
// CHECK-NOT: __riscv_ssstateen {{.*$}}
// CHECK-NOT: __riscv_ssstrict {{.*$}}
@@ -1347,6 +1350,36 @@
// RUN: -o - | FileCheck --check-prefix=CHECK-SSCSRIND-EXT %s
// CHECK-SSCSRIND-EXT: __riscv_sscsrind 1000000{{$}}
+// RUN: %clang --target=riscv32 \
+// RUN: -march=rv32isspmp1p0 -E -dM %s \
+// RUN: -o - | FileCheck --check-prefix=CHECK-SSPMP-EXT %s
+// RUN: %clang --target=riscv64 \
+// RUN: -march=rv64isspmp1p0 -E -dM %s \
+// RUN: -o - | FileCheck --check-prefix=CHECK-SSPMP-EXT %s
+// CHECK-SSPMP-EXT: __riscv_sscsrind 1000000{{$}}
+// CHECK-SSPMP-EXT: __riscv_sspmp 1000000{{$}}
+
+// RUN: %clang --target=riscv32 \
+// RUN: -march=rv32isspmpen1p0 -E -dM %s \
+// RUN: -o - | FileCheck --check-prefix=CHECK-SSPMPEN-EXT %s
+// RUN: %clang --target=riscv64 \
+// RUN: -march=rv64isspmpen1p0 -E -dM %s \
+// RUN: -o - | FileCheck --check-prefix=CHECK-SSPMPEN-EXT %s
+// CHECK-SSPMPEN-EXT: __riscv_sscsrind 1000000{{$}}
+// CHECK-SSPMPEN-EXT: __riscv_sspmp 1000000{{$}}
+// CHECK-SSPMPEN-EXT: __riscv_sspmpen 1000000{{$}}
+
+// RUN: %clang --target=riscv32 \
+// RUN: -march=rv32ismpmpdeleg1p0 -E -dM %s \
+// RUN: -o - | FileCheck --check-prefix=CHECK-SMPMPDELEG-EXT %s
+// RUN: %clang --target=riscv64 \
+// RUN: -march=rv64ismpmpdeleg1p0 -E -dM %s \
+// RUN: -o - | FileCheck --check-prefix=CHECK-SMPMPDELEG-EXT %s
+// CHECK-SMPMPDELEG-EXT: __riscv_smcsrind 1000000{{$}}
+// CHECK-SMPMPDELEG-EXT: __riscv_smpmpdeleg 1000000{{$}}
+// CHECK-SMPMPDELEG-EXT: __riscv_sscsrind 1000000{{$}}
+// CHECK-SMPMPDELEG-EXT: __riscv_sspmp 1000000{{$}}
+
// RUN: %clang --target=riscv32 \
// RUN: -march=rv32ismdbltrp1p0 -E -dM %s \
// RUN: -o - | FileCheck --check-prefix=CHECK-SMDBLTRP-EXT %s
diff --git a/llvm/docs/RISCVUsage.rst b/llvm/docs/RISCVUsage.rst
index 548f25ac2e596..c24210d7f1871 100644
--- a/llvm/docs/RISCVUsage.rst
+++ b/llvm/docs/RISCVUsage.rst
@@ -139,6 +139,7 @@ on support follow.
``Smepmp`` Supported
``Smmpm`` Supported
``Smnpm`` Supported
+ ``Smpmpdeleg`` Support
``Smrnmi`` Supported
``Smstateen`` Assembly Support
``Ssaia`` Supported
@@ -151,6 +152,8 @@ on support follow.
``Ssdbltrp`` Supported
``Ssnpm`` Supported
``Sspm`` Supported
+ ``Sspmp`` Support
+ ``Sspmpen`` Support
``Ssqosid`` Assembly Support
``Ssstateen`` Assembly Support (`See note <#riscv-profiles-extensions-note>`__)
``Ssstrict`` Assembly Support (`See note <#riscv-profiles-extensions-note>`__)
diff --git a/llvm/lib/Target/RISCV/RISCVFeatures.td b/llvm/lib/Target/RISCV/RISCVFeatures.td
index 361be64352499..ecb238094852d 100644
--- a/llvm/lib/Target/RISCV/RISCVFeatures.td
+++ b/llvm/lib/Target/RISCV/RISCVFeatures.td
@@ -1095,6 +1095,16 @@ def FeatureStdExtSsccfg
def FeatureStdExtSsccptr
: RISCVExtension<1, 0, "Main memory supports page table reads">;
+def FeatureStdExtSspmp
+ : RISCVExtension<1, 0, "S-level Physical Memory Protection (SPMP)",
+ [FeatureStdExtSscsrind]>;
+def FeatureStdExtSspmpen
+ : RISCVExtension<1, 0, "Optimizing Context Switching of SPMP Entries", [FeatureStdExtSspmp]>;
+
+def FeatureStdExtSmpmpdeleg
+ : RISCVExtension<1, 0, "Sharing Hardware Resources between PMP and SPMP",
+ [FeatureStdExtSmcsrind, FeatureStdExtSspmp]>;
+
def FeatureStdExtSscofpmf
: RISCVExtension<1, 0, "Count Overflow and Mode-Based Filtering">;
diff --git a/llvm/lib/Target/RISCV/RISCVSystemOperands.td b/llvm/lib/Target/RISCV/RISCVSystemOperands.td
index 66e3484ff0955..463d209214785 100644
--- a/llvm/lib/Target/RISCV/RISCVSystemOperands.td
+++ b/llvm/lib/Target/RISCV/RISCVSystemOperands.td
@@ -166,6 +166,9 @@ def : SysReg<"scountovf", 0xDA0>;
def : SysReg<"satp", 0x180>;
let isDeprecatedName = 1 in
def : SysReg<"sptbr", 0x180>;
+def : SysReg<"spmpen", 0x183>;
+let isRV32Only = 1 in
+def : SysReg<"spmpenh", 0x193>;
//===----------------------------------------------------------------------===//
// Supervisor Timer Compare
@@ -324,6 +327,7 @@ def : SysReg<"mtval2", 0x34B>;
def : SysReg<"menvcfg", 0x30A>;
let isRV32Only = 1 in
def : SysReg<"menvcfgh", 0x31A>;
+def : SysReg<"mpmpdeleg", 0x316>;
def : SysReg<"mseccfg", 0x747>;
let isRV32Only = 1 in
def : SysReg<"mseccfgh", 0x757>;
diff --git a/llvm/test/CodeGen/RISCV/features-info.ll b/llvm/test/CodeGen/RISCV/features-info.ll
index 8abe64b8ecda4..4117e38d9c47d 100644
--- a/llvm/test/CodeGen/RISCV/features-info.ll
+++ b/llvm/test/CodeGen/RISCV/features-info.ll
@@ -164,6 +164,7 @@
; CHECK-NEXT: smepmp - 'Smepmp' (Enhanced Physical Memory Protection).
; CHECK-NEXT: smmpm - 'Smmpm' (Machine-level Pointer Masking for M-mode).
; CHECK-NEXT: smnpm - 'Smnpm' (Machine-level Pointer Masking for next lower privilege mode).
+; CHECK-NEXT: smpmpdeleg - 'Smpmpdeleg' (Sharing Hardware Resources between PMP and SPMP).
; CHECK-NEXT: smrnmi - 'Smrnmi' (Resumable Non-Maskable Interrupts).
; CHECK-NEXT: smstateen - 'Smstateen' (Machine-mode view of the state-enable extension).
; CHECK-NEXT: ssaia - 'Ssaia' (Advanced Interrupt Architecture Supervisor Level).
@@ -176,6 +177,8 @@
; CHECK-NEXT: ssdbltrp - 'Ssdbltrp' (Double Trap Supervisor Level).
; CHECK-NEXT: ssnpm - 'Ssnpm' (Supervisor-level Pointer Masking for next lower privilege mode).
; CHECK-NEXT: sspm - 'Sspm' (Indicates Supervisor-mode Pointer Masking).
+; CHECK-NEXT: sspmp - 'Sspmp' (S-level Physical Memory Protection (SPMP)).
+; CHECK-NEXT: sspmpen - 'Sspmpen' (Optimizing Context Switching of SPMP Entries).
; CHECK-NEXT: ssqosid - 'Ssqosid' (Quality-of-Service (QoS) Identifiers).
; CHECK-NEXT: ssstateen - 'Ssstateen' (Supervisor-mode view of the state-enable extension).
; CHECK-NEXT: ssstrict - 'Ssstrict' (No non-conforming extensions are present).
diff --git a/llvm/test/MC/RISCV/attribute-arch.s b/llvm/test/MC/RISCV/attribute-arch.s
index 367ec6f04d953..53a2a0527ceed 100644
--- a/llvm/test/MC/RISCV/attribute-arch.s
+++ b/llvm/test/MC/RISCV/attribute-arch.s
@@ -357,6 +357,9 @@
.attribute arch, "rv32i_smepmp1p0"
# CHECK: attribute 5, "rv32i2p1_smepmp1p0"
+.attribute arch, "rv32i_smpmpdeleg1p0"
+# CHECK: attribute 5, "rv32i2p1_smcsrind1p0_smpmpdeleg1p0_sscsrind1p0_sspmp1p0"
+
.attribute arch, "rv32i_smpmpmt0p6"
# CHECK: attribute 5, "rv32i2p1_smpmpmt0p6"
@@ -375,6 +378,12 @@
.attribute arch, "rv32i_sscounterenw1p0"
# CHECK: attribute 5, "rv32i2p1_sscounterenw1p0"
+.attribute arch, "rv32i_sspmp1p0"
+# CHECK: attribute 5, "rv32i2p1_sscsrind1p0_sspmp1p0"
+
+.attribute arch, "rv32i_sspmpen1p0"
+# CHECK: attribute 5, "rv32i2p1_sscsrind1p0_sspmp1p0_sspmpen1p0"
+
.attribute arch, "rv32i_ssqosid1p0"
# CHECK: attribute 5, "rv32i2p1_ssqosid1p0"
diff --git a/llvm/test/MC/RISCV/spmp-csr-names.s b/llvm/test/MC/RISCV/spmp-csr-names.s
new file mode 100644
index 0000000000000..fb6bce657b351
--- /dev/null
+++ b/llvm/test/MC/RISCV/spmp-csr-names.s
@@ -0,0 +1,50 @@
+# RUN: llvm-mc %s -triple=riscv32 -M no-aliases -show-encoding \
+# RUN: | FileCheck -check-prefixes=CHECK-INST,CHECK-ENC %s
+# RUN: llvm-mc -filetype=obj -triple riscv32 < %s \
+# RUN: | llvm-objdump -d - \
+# RUN: | FileCheck -check-prefix=CHECK-INST-ALIAS %s
+# RUN: llvm-mc %s -triple=riscv64 -M no-aliases -show-encoding \
+# RUN: | FileCheck -check-prefixes=CHECK-INST,CHECK-ENC %s
+# RUN: llvm-mc -filetype=obj -triple riscv64 < %s \
+# RUN: | llvm-objdump -d - \
+# RUN: | FileCheck -check-prefix=CHECK-INST-ALIAS %s
+# RUN: llvm-mc %s -triple=riscv32 -defsym=RV32=1 -M no-aliases -show-encoding \
+# RUN: | FileCheck -check-prefixes=RV32-INST,RV32-ENC %s
+# RUN: llvm-mc -filetype=obj -triple riscv32 -defsym=RV32=1 < %s \
+# RUN: | llvm-objdump -d - \
+# RUN: | FileCheck -check-prefix=RV32-ALIAS %s
+# RUN: not llvm-mc %s -triple=riscv64 -defsym=RV32=1 2>&1 \
+# RUN: | FileCheck -check-prefix=CHECK-RV64-ERR %s
+
+# spmpen
+# CHECK-INST: csrrs t1, spmpen, zero
+# CHECK-ENC: encoding: [0x73,0x23,0x30,0x18]
+# CHECK-INST-ALIAS: csrr t1, spmpen
+# CHECK-INST: csrrs t2, spmpen, zero
+# CHECK-ENC: encoding: [0xf3,0x23,0x30,0x18]
+# CHECK-INST-ALIAS: csrr t2, spmpen
+csrrs t1, spmpen, zero
+csrrs t2, 0x183, zero
+
+# mpmpdeleg
+# CHECK-INST: csrrs t1, mpmpdeleg, zero
+# CHECK-ENC: encoding: [0x73,0x23,0x60,0x31]
+# CHECK-INST-ALIAS: csrr t1, mpmpdeleg
+# CHECK-INST: csrrs t2, mpmpdeleg, zero
+# CHECK-ENC: encoding: [0xf3,0x23,0x60,0x31]
+# CHECK-INST-ALIAS: csrr t2, mpmpdeleg
+csrrs t1, mpmpdeleg, zero
+csrrs t2, 0x316, zero
+
+.ifdef RV32
+# spmpenh
+# RV32-INST: csrrs t1, spmpenh, zero
+# RV32-ENC: encoding: [0x73,0x23,0x30,0x19]
+# RV32-ALIAS: csrr t1, spmpenh
+# RV32-INST: csrrs t2, spmpenh, zero
+# RV32-ENC: encoding: [0xf3,0x23,0x30,0x19]
+# RV32-ALIAS: csrr t2, spmpenh
+# CHECK-RV64-ERR: error: system register 'spmpenh' is RV32 only
+csrrs t1, spmpenh, zero
+csrrs t2, 0x193, zero
+.endif
diff --git a/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp b/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp
index 837a72913dc7d..ea0c1dbd9b6e8 100644
--- a/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp
+++ b/llvm/unittests/TargetParser/RISCVISAInfoTest.cpp
@@ -1504,6 +1504,7 @@ R"(All available -march extensions for RISC-V
smepmp 1.0
smmpm 1.0
smnpm 1.0
+ smpmpdeleg 1.0
smrnmi 1.0
smstateen 1.0
ssaia 1.0
@@ -1516,6 +1517,8 @@ R"(All available -march extensions for RISC-V
ssdbltrp 1.0
ssnpm 1.0
sspm 1.0
+ sspmp 1.0
+ sspmpen 1.0
ssqosid 1.0
ssstateen 1.0
ssstrict 1.0
More information about the cfe-commits
mailing list