[PATCH] arm64: kgdb: Fix interrupt-induced single-step exception

liuqiqi at kylinos.cn liuqiqi at kylinos.cn
Sun Jun 14 22:29:03 PDT 2026


From: Qiqi Liu <liuqiqi at kylinos.cn>

After entering kdb due to breakpoint, when we execute 'ss' or 'go'
(will delay installing breakpoints, do single-step first),
and it will enter kdb again.
We found that due to context switching caused by interrupt, 
the instruction at ss is no longer the original breakpoint instruction.

Before the patch:
[root at localhost ~]# echo g > /proc/sysrq-trigger
Entering kdb (current=0xffff030004f2bc00, pid 8818) on processor 15 due to Keyboard Entry
[15]kdb> bp sysctl_vm_numa_stat_handler
Instruction(i) BP #0 at 0xffffae550650c810 (sysctl_vm_numa_stat_handler)
    is enabled    addr at 0xffffae550650c810, hardtype=0 installed=0
[15]kdb> g
[root at localhost ~]# echo 1 > /proc/sys/vm/numa_stat
Entering kdb (current=0xffff030004f2bc00, pid 8818) on processor 12 due to Breakpoint @ 0xffffae550650c810
[12]kdb> g
Entering kdb (current=0xffff030004f2bc00, pid 8818) on processor 12 due to Breakpoint @ 0xffffae550650c810
[12]kdb> g

After the patch:
[root at localhost ~]# echo g > /proc/sysrq-trigger
Entering kdb (current=0xfffff010012c36400, pid 6488) on processor 41 due to Keyboard Entry
[41]kdb> bp sysctl_vm_numa_stat_handler
Instruction(i) BP #0 at 0xfffffd1768c2dc7c8 (sysctl_vm_numa_stat_handler)
    is enabled    addr at ffffdf1768c2dc7c8, hardtype=0 installed=0
[41]kdb> g
[root at localhost ~]# echo 1 > /proc/sys/vm/numa_stat
Entering kdb (current=0xfffff010012c36400, pid 6488) on processor 7 due to Breakpoint @ 0xfffffd1768c2dc7c8
[7]kdb> g
[root at localhost ~]#

Fixes: 44679a4f142b ("arm64: KGDB: Add step debugging support")
Co-developed-by: Tongbo Wei <kf.weitongbo at h3c.com>
Signed-off-by: Tongbo Wei <kf.weitongbo at h3c.com>
Signed-off-by: Qiqi Liu <liuqiqi at kylinos.cn>
---
 arch/arm64/kernel/kgdb.c | 12 ++++++++++++
 1 file changed, 12 insertions(+)

diff --git a/arch/arm64/kernel/kgdb.c b/arch/arm64/kernel/kgdb.c
index 968324a79a89..e9a246a0c34f 100644
--- a/arch/arm64/kernel/kgdb.c
+++ b/arch/arm64/kernel/kgdb.c
@@ -101,6 +101,8 @@ struct dbg_reg_def_t dbg_reg_def[DBG_MAX_REG_NUM] = {
 	{ "fpcr", 4, -1 },
 };
 
+static DEFINE_PER_CPU(unsigned int, kgdb_pstate);
+
 char *dbg_get_reg(int regno, void *mem, struct pt_regs *regs)
 {
 	if (regno >= DBG_MAX_REG_NUM || regno < 0)
@@ -207,6 +209,8 @@ int kgdb_arch_handle_exception(int exception_vector, int signo,
 		err = 0;
 		break;
 	case 's':
+		__this_cpu_write(kgdb_pstate, linux_regs->pstate);
+		linux_regs->pstate |= PSR_I_BIT;
 		/*
 		 * Update step address value with address passed
 		 * with step packet.
@@ -252,9 +256,17 @@ NOKPROBE_SYMBOL(kgdb_compiled_brk_handler);
 
 int kgdb_single_step_handler(struct pt_regs *regs, unsigned long esr)
 {
+	unsigned int pstate;
 	if (!kgdb_single_step)
 		return DBG_HOOK_ERROR;
 
+	/* restore interrupt mask status */
+	pstate = __this_cpu_read(kgdb_pstate);
+	if (pstate & PSR_I_BIT)
+		regs->pstate |= PSR_I_BIT;
+	else
+		regs->pstate &= ~PSR_I_BIT;
+
 	kgdb_handle_exception(0, SIGTRAP, 0, regs);
 	return DBG_HOOK_HANDLED;
 }
-- 
2.25.1




More information about the linux-arm-kernel mailing list