Linux-ARM-Kernel Archive on lore.kernel.org
 help / color / mirror / Atom feed
* [RFC PATCH] arm64: mm: recover from kernel-mode SEA via exception table
@ 2026-09-12 13:55 Nguyen Ngoc Thang
  0 siblings, 0 replies; only message in thread
From: Nguyen Ngoc Thang @ 2026-09-12 13:55 UTC (permalink / raw)
  To: Catalin Marinas, Will Deacon
  Cc: Mark Rutland, linux-arm-kernel, linux-kernel,
	syzbot+635d160c0d4133481520, syzkaller-bugs, Nguyen Ngoc Thang

do_sea() unconditionally calls die() for a synchronous external
abort taken at EL1, without ever consulting the exception table.
This is inconsistent with __do_kernel_fault(), which does check
fixup_exception() before giving up.

A SEA at EL1 is reachable and recoverable: futex's LL/SC atomic ops
(__llsc_futex_cmpxchg/__llsc_futex_atomic_*) carry
_ASM_EXTABLE_UACCESS_ERR entries, but if the user address is mapped
to Device memory (e.g. a PCI BAR obtained via sysfs "resourceN" and
mmap'd MAP_FIXED), the LDXR/STLXR pair faults with a SEA instead of
a translation fault, and the extable fixup is never reached, so the
kernel oopses instead of returning -EFAULT to userspace.

Check fixup_exception() for kernel-mode SEAs before dying, mirroring
__do_kernel_fault(). No taint is added on the recovered path since
this is a userspace-triggerable condition, not a hardware failure;
a ratelimited warning keeps a trace of it.

Reported-by: syzbot+635d160c0d4133481520@syzkaller.appspotmail.com
Link: https://syzkaller.appspot.com/bug?extid=635d160c0d4133481520
Signed-off-by: Nguyen Ngoc Thang <ngocthang2710.1999@gmail.com>
---
Sent as RFC: verified by code inspection (ESR/DFSC decode matches
the extable-carrying LL/SC futex path) but not yet reproduced under
QEMU on my end; would appreciate a look before I chase the aarch64
repro further.

 arch/arm64/mm/fault.c | 12 ++++++++++++
 1 file changed, 12 insertions(+)

diff --git a/arch/arm64/mm/fault.c b/arch/arm64/mm/fault.c
index 0b52557652be..fe5a5c5bbc27 100644
--- a/arch/arm64/mm/fault.c
+++ b/arch/arm64/mm/fault.c
@@ -878,6 +878,18 @@ static int do_sea(unsigned long far, unsigned long esr, struct pt_regs *regs)
 		return 0;
 	}
 
+	/*
+	 * A SEA at EL1 can happen from uaccess helpers (e.g. LDXR/STLXR
+	 * on a user page mapped as Device memory, as in the futex ops)
+	 * that carry an extable fixup. Let it return -EFAULT instead of
+	 * oopsing the kernel.
+	 */
+	if (!user_mode(regs) && fixup_exception(regs, esr)) {
+		pr_warn_ratelimited("Recovered SEA at kernel uaccess, addr=%#lx, esr=%#lx\n",
+				    far, esr);
+		return 0;
+	}
+
 	if (esr & ESR_ELx_FnV) {
 		siaddr = 0;
 	} else {
-- 
2.43.0



^ permalink raw reply related	[flat|nested] only message in thread

only message in thread, other threads:[~2026-09-12 13:56 UTC | newest]

Thread overview: (only message) (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-09-12 13:55 [RFC PATCH] arm64: mm: recover from kernel-mode SEA via exception table Nguyen Ngoc Thang

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox