[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-Id: <20251118025015.42491-2-cuiyunhui@bytedance.com>
Date: Tue, 18 Nov 2025 10:50:08 +0800
From: Yunhui Cui <cuiyunhui@...edance.com>
To: conor@...nel.org,
paul.walmsley@...ive.com,
palmer@...belt.com,
aou@...s.berkeley.edu,
alex@...ti.fr,
cuiyunhui@...edance.com,
luxu.kernel@...edance.com,
linux-kernel@...r.kernel.org,
linux-riscv@...ts.infradead.org,
jassisinghbrar@...il.com,
conor.dooley@...rochip.com,
valentina.fernandezalanis@...rochip.com,
catalin.marinas@....com,
will@...nel.org,
maz@...nel.org,
timothy.hayes@....com,
lpieralisi@...nel.org,
arnd@...db.de,
kees@...nel.org,
tglx@...utronix.de,
viresh.kumar@...aro.org,
boqun.feng@...il.com,
linux-arm-kernel@...ts.infradead.org,
cleger@...osinc.com,
atishp@...osinc.com,
ajones@...tanamicro.com
Subject: [PATCH v2 1/8] drivers: firmware: riscv: add SSE NMI support
Add support for handling Non-Maskable Interrupts (NMIs) through the
RISC-V Supervisor Software Events (SSE) framework. Add basic NMI
functionality via SBI_SSE_EVENT_LOCAL_SOFTWARE_INJECTED registration
and enabling.
Signed-off-by: Yunhui Cui <cuiyunhui@...edance.com>
---
MAINTAINERS | 8 +++
drivers/firmware/riscv/Kconfig | 10 +++
drivers/firmware/riscv/Makefile | 1 +
drivers/firmware/riscv/riscv_sse_nmi.c | 89 ++++++++++++++++++++++++++
include/linux/riscv_sse_nmi.h | 26 ++++++++
5 files changed, 134 insertions(+)
create mode 100644 drivers/firmware/riscv/riscv_sse_nmi.c
create mode 100644 include/linux/riscv_sse_nmi.h
diff --git a/MAINTAINERS b/MAINTAINERS
index 8bf5416953f45..c06658da8af96 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -22057,6 +22057,14 @@ S: Maintained
F: drivers/firmware/riscv/riscv_sse.c
F: include/linux/riscv_sse.h
+RISC-V SSE NMI SUPPORT
+M: Yunhui Cui <cuiyunhui@...edance.com>
+R: Xu Lu <luxu.kernel@...edance.com>
+L: linux-riscv@...ts.infradead.org
+S: Maintained
+F: drivers/firmware/riscv/riscv_sse_nmi.c
+F: include/linux/riscv_sse_nmi.h
+
RISC-V THEAD SoC SUPPORT
M: Drew Fustini <fustini@...nel.org>
M: Guo Ren <guoren@...nel.org>
diff --git a/drivers/firmware/riscv/Kconfig b/drivers/firmware/riscv/Kconfig
index ed5b663ac5f91..6c77c7823571a 100644
--- a/drivers/firmware/riscv/Kconfig
+++ b/drivers/firmware/riscv/Kconfig
@@ -12,4 +12,14 @@ config RISCV_SBI_SSE
this option provides support to register callbacks on specific SSE
events.
+config RISCV_SSE_NMI
+ bool "Enable SBI Supervisor Software Events NMI support"
+ depends on RISCV_SBI_SSE && SMP
+ default y
+ help
+ This option enables support for delivering Non-Maskable Interrupt
+ (NMI) notifications through the Supervisor Software Events (SSE)
+ framework. When enabled, the system can deliver local, unknown and
+ other types of NMIs.
+
endmenu
diff --git a/drivers/firmware/riscv/Makefile b/drivers/firmware/riscv/Makefile
index c8795d4bbb2ea..fbc182b53ae53 100644
--- a/drivers/firmware/riscv/Makefile
+++ b/drivers/firmware/riscv/Makefile
@@ -1,3 +1,4 @@
# SPDX-License-Identifier: GPL-2.0
obj-$(CONFIG_RISCV_SBI_SSE) += riscv_sbi_sse.o
+obj-$(CONFIG_RISCV_SSE_NMI) += riscv_sse_nmi.o
diff --git a/drivers/firmware/riscv/riscv_sse_nmi.c b/drivers/firmware/riscv/riscv_sse_nmi.c
new file mode 100644
index 0000000000000..1763f43961ab6
--- /dev/null
+++ b/drivers/firmware/riscv/riscv_sse_nmi.c
@@ -0,0 +1,89 @@
+/* SPDX-License-Identifier: GPL-2.0-or-later */
+
+#define pr_fmt(fmt) "SSE NMI: " fmt
+
+#include <linux/atomic.h>
+#include <linux/riscv_sbi_sse.h>
+#include <linux/riscv_sse_nmi.h>
+
+#include <asm/irq_regs.h>
+#include <asm/sbi.h>
+#include <asm/smp.h>
+
+bool nmi_available;
+static struct sse_event *local_nmi_evt;
+static atomic_t local_nmi_arg = ATOMIC_INIT(LOCAL_NMI_NONE);
+
+bool nmi_support(void)
+{
+ return READ_ONCE(nmi_available);
+}
+
+static inline struct sbiret sbi_sse_ecall(int fid, unsigned long arg0,
+ unsigned long arg1)
+{
+ return sbi_ecall(SBI_EXT_SSE, fid, arg0, arg1, 0, 0, 0, 0);
+}
+
+void send_nmi_single(unsigned int cpu, enum local_nmi_type type)
+{
+ unsigned int hart_id = cpuid_to_hartid_map(cpu);
+ u32 evt = SBI_SSE_EVENT_LOCAL_SOFTWARE_INJECTED;
+ struct sbiret ret;
+
+ atomic_or(type, &local_nmi_arg);
+ ret = sbi_sse_ecall(SBI_SSE_EVENT_INJECT, evt, hart_id);
+ if (ret.error)
+ pr_err("Failed to signal event %x to hartid %d, error %ld\n",
+ evt, hart_id, ret.error);
+}
+
+void send_nmi_mask(cpumask_t *mask, enum local_nmi_type type)
+{
+ unsigned int cpu;
+
+ for_each_cpu(cpu, mask)
+ send_nmi_single(cpu, type);
+}
+
+static int local_nmi_handler(u32 evt, void *arg, struct pt_regs *regs)
+{
+ return 0;
+}
+
+static int __init local_nmi_init(void)
+{
+ int ret;
+
+ local_nmi_evt = sse_event_register(SBI_SSE_EVENT_LOCAL_SOFTWARE_INJECTED, 0,
+ local_nmi_handler, &local_nmi_arg);
+ if (IS_ERR(local_nmi_evt))
+ return PTR_ERR(local_nmi_evt);
+
+ ret = sse_event_enable(local_nmi_evt);
+ if (ret) {
+ sse_event_unregister(local_nmi_evt);
+ return ret;
+ }
+
+ pr_info("Using SSE for Local NMI event delivery\n");
+
+ return 0;
+}
+
+static int __init sse_nmi_init(void)
+{
+ int ret;
+
+ ret = local_nmi_init();
+ if (ret) {
+ pr_err("Local_nmi_init failed with error %d\n", ret);
+ return ret;
+ }
+
+ WRITE_ONCE(nmi_available, true);
+
+ return 0;
+}
+
+late_initcall(sse_nmi_init);
diff --git a/include/linux/riscv_sse_nmi.h b/include/linux/riscv_sse_nmi.h
new file mode 100644
index 0000000000000..16db85c5162f5
--- /dev/null
+++ b/include/linux/riscv_sse_nmi.h
@@ -0,0 +1,26 @@
+/* SPDX-License-Identifier: GPL-2.0-or-later */
+
+#ifndef __LINUX_RISCV_SSE_NMI_H
+#define __LINUX_RISCV_SSE_NMI_H
+
+#include <linux/cpumask.h>
+
+enum local_nmi_type {
+ LOCAL_NMI_NONE = 0U,
+ LOCAL_NMI_STOP = BIT(0),
+ LOCAL_NMI_CRASH = BIT(1),
+ LOCAL_NMI_BACKTRACE = BIT(2),
+ LOCAL_NMI_KGDB = BIT(3),
+};
+
+#ifdef CONFIG_RISCV_SSE_NMI
+bool nmi_support(void);
+void send_nmi_mask(cpumask_t *mask, enum local_nmi_type type);
+void send_nmi_single(unsigned int cpu, enum local_nmi_type type);
+#else
+static inline bool nmi_support(void) { return false; }
+static inline void send_nmi_mask(cpumask_t *mask) { };
+static inline void send_nmi_single(unsigned int cpu) { };
+#endif
+
+#endif
--
2.39.5
Powered by blists - more mailing lists