linux-arm-kernel.lists.infradead.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases
@ 2021-12-07 18:32 Mark Rutland
  2021-12-07 18:32 ` [PATCH v2 1/2] arm64: mm: use die_kernel_fault() in do_mem_abort() Mark Rutland
                   ` (4 more replies)
  0 siblings, 5 replies; 6+ messages in thread
From: Mark Rutland @ 2021-12-07 18:32 UTC (permalink / raw)
  To: linux-arm-kernel
  Cc: andreyknvl, catalin.marinas, dvyukov, glider, mark.rutland,
	ryabinin.a.a, will

When using KASAN_GENERIC or KASAN_SW_TAGS, many representable pointer
values (e.g. NULL) don't have a legitimate shadow address. If KASAN
instrumentation attempts to access the shadow for such pointers, it will
fault on an unusual-looking address, e.g.

| Unable to handle kernel paging request at virtual address dfff800000000001

To make this easier to debug, this series makes the arm64 fault handling
code log the corresponding memory range for potential shadow acceses,
e.g.

| Unable to handle kernel paging request at virtual address dfff800000000017
| KASAN: null-ptr-deref in range [0x00000000000000b8-0x00000000000000bf]

Since v1 [1]:
* Use kasan_non_canonical_hook()
* Drop move of kasan_shadow_to_mem()
* Update commit messages

[1] https://lore.kernel.org/r/20211202112731.3346975-1-mark.rutland@arm.com

Thanks,
Mark.

Mark Rutland (2):
  arm64: mm: use die_kernel_fault() in do_mem_abort()
  arm64: mm: log potential KASAN shadow alias

 arch/arm64/mm/fault.c | 9 ++++-----
 1 file changed, 4 insertions(+), 5 deletions(-)

-- 
2.30.2


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply	[flat|nested] 6+ messages in thread

* [PATCH v2 1/2] arm64: mm: use die_kernel_fault() in do_mem_abort()
  2021-12-07 18:32 [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases Mark Rutland
@ 2021-12-07 18:32 ` Mark Rutland
  2021-12-07 18:32 ` [PATCH v2 2/2] arm64: mm: log potential KASAN shadow alias Mark Rutland
                   ` (3 subsequent siblings)
  4 siblings, 0 replies; 6+ messages in thread
From: Mark Rutland @ 2021-12-07 18:32 UTC (permalink / raw)
  To: linux-arm-kernel
  Cc: andreyknvl, catalin.marinas, dvyukov, glider, mark.rutland,
	ryabinin.a.a, will

If we take an unhandled fault from EL1, either:

a) The xFSC handler calls die_kernel_fault() directly. In this case,
   die_kernel_fault() calls:

   pr_alert(..., msg, addr);
   mem_abort_decode(esr);
   show_pte(addr);
   die();
   bust_spinlocks(0);
   do_exit(SIGKILL);

b) The xFSC handler returns to do_mem_abort(), indicating failure. In
   this case, do_mem_abort() calls:

   pr_alert(..., addr);
   mem_abort_decode(esr);
   show_pte(addr);
   arm64_notify_die() {
     die();
   }

This inconstency is unfortunatem, and in theory in case (b) registered
notifiers can prevent us from terminating the faulting thread by
returning NOTIFY_STOP, whereupon we'll end up returning from the fault,
replaying, and almost certainly get stuck in a livelock spewing errors
into dmesg. We don't expect notifers to fix things up, since we dump
state to dmesg before invoking them, so it would be more sensible to
consistently terminate the thread in this case.

This patch has do_mem_abort() call die_kernel_fault() for unhandled
faults taken from EL1. Where we would previously have logged a messafe
of the form:

| Unhandled fault at ${ADDR}

... we will now log a message of the form:

| Unable to handle kernel ${FAULT_NAME} at virtual address ${ADDR}

... and we will consistently terminate the thread from which the fault
was taken.

Signed-off-by: Mark Rutland <mark.rutland@arm.com>
Cc: Catalin Marinas <catalin.marinas@arm.com>
Cc: Will Deacon <will@kernel.org>
---
 arch/arm64/mm/fault.c | 7 ++-----
 1 file changed, 2 insertions(+), 5 deletions(-)

diff --git a/arch/arm64/mm/fault.c b/arch/arm64/mm/fault.c
index 9ae24e3b72be..b7b9caa41bc7 100644
--- a/arch/arm64/mm/fault.c
+++ b/arch/arm64/mm/fault.c
@@ -813,11 +813,8 @@ void do_mem_abort(unsigned long far, unsigned int esr, struct pt_regs *regs)
 	if (!inf->fn(far, esr, regs))
 		return;
 
-	if (!user_mode(regs)) {
-		pr_alert("Unhandled fault at 0x%016lx\n", addr);
-		mem_abort_decode(esr);
-		show_pte(addr);
-	}
+	if (!user_mode(regs))
+		die_kernel_fault(inf->name, addr, esr, regs);
 
 	/*
 	 * At this point we have an unrecognized fault type whose tag bits may
-- 
2.30.2


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply related	[flat|nested] 6+ messages in thread

* [PATCH v2 2/2] arm64: mm: log potential KASAN shadow alias
  2021-12-07 18:32 [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases Mark Rutland
  2021-12-07 18:32 ` [PATCH v2 1/2] arm64: mm: use die_kernel_fault() in do_mem_abort() Mark Rutland
@ 2021-12-07 18:32 ` Mark Rutland
  2021-12-10 17:46 ` [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases Andrey Konovalov
                   ` (2 subsequent siblings)
  4 siblings, 0 replies; 6+ messages in thread
From: Mark Rutland @ 2021-12-07 18:32 UTC (permalink / raw)
  To: linux-arm-kernel
  Cc: andreyknvl, catalin.marinas, dvyukov, glider, mark.rutland,
	ryabinin.a.a, will

When the kernel is built with KASAN_GENERIC or KASAN_SW_TAGS, shadow
memory is allocated and mapped for all legitimate kernel addresses, and
prior to a regular memory access instrumentation will read from the
corresponding shadow address.

Due to the way memory addresses are converted to shadow addresses, bogus
pointers (e.g. NULL) can generate shadow addresses out of the bounds of
allocated shadow memory. For example, with KASAN_GENERIC and 48-bit VAs,
NULL would have a shadow address of dfff800000000000, which falls
between the TTBR ranges.

To make such cases easier to debug, this patch makes die_kernel_fault()
dump the real memory address range for any potential KASAN shadow access
using kasan_non_canonical_hook(), which results in fault information as
below when KASAN is enabled:

| Unable to handle kernel paging request at virtual address dfff800000000017
| KASAN: null-ptr-deref in range [0x00000000000000b8-0x00000000000000bf]
| Mem abort info:
|   ESR = 0x96000004
|   EC = 0x25: DABT (current EL), IL = 32 bits
|   SET = 0, FnV = 0
|   EA = 0, S1PTW = 0
|   FSC = 0x04: level 0 translation fault
| Data abort info:
|   ISV = 0, ISS = 0x00000004
|   CM = 0, WnR = 0
| [dfff800000000017] address between user and kernel address ranges

Signed-off-by: Mark Rutland <mark.rutland@arm.com>
Cc: Alexander Potapenko <glider@google.com>
Cc: Andrey Konovalov <andreyknvl@gmail.com>
Cc: Andrey Ryabinin <ryabinin.a.a@gmail.com>
Cc: Catalin Marinas <catalin.marinas@arm.com>
Cc: Dmitry Vyukov <dvyukov@google.com>
Cc: Will Deacon <will@kernel.org>
---
 arch/arm64/mm/fault.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/arch/arm64/mm/fault.c b/arch/arm64/mm/fault.c
index b7b9caa41bc7..9a9e7675b187 100644
--- a/arch/arm64/mm/fault.c
+++ b/arch/arm64/mm/fault.c
@@ -297,6 +297,8 @@ static void die_kernel_fault(const char *msg, unsigned long addr,
 	pr_alert("Unable to handle kernel %s at virtual address %016lx\n", msg,
 		 addr);
 
+	kasan_non_canonical_hook(addr);
+
 	mem_abort_decode(esr);
 
 	show_pte(addr);
-- 
2.30.2


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply related	[flat|nested] 6+ messages in thread

* Re: [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases
  2021-12-07 18:32 [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases Mark Rutland
  2021-12-07 18:32 ` [PATCH v2 1/2] arm64: mm: use die_kernel_fault() in do_mem_abort() Mark Rutland
  2021-12-07 18:32 ` [PATCH v2 2/2] arm64: mm: log potential KASAN shadow alias Mark Rutland
@ 2021-12-10 17:46 ` Andrey Konovalov
  2021-12-13 18:24 ` Will Deacon
  2021-12-13 19:18 ` Catalin Marinas
  4 siblings, 0 replies; 6+ messages in thread
From: Andrey Konovalov @ 2021-12-10 17:46 UTC (permalink / raw)
  To: Mark Rutland
  Cc: Linux ARM, Catalin Marinas, Dmitry Vyukov, Alexander Potapenko,
	Andrey Ryabinin, Will Deacon

On Tue, Dec 7, 2021 at 7:32 PM Mark Rutland <mark.rutland@arm.com> wrote:
>
> When using KASAN_GENERIC or KASAN_SW_TAGS, many representable pointer
> values (e.g. NULL) don't have a legitimate shadow address. If KASAN
> instrumentation attempts to access the shadow for such pointers, it will
> fault on an unusual-looking address, e.g.
>
> | Unable to handle kernel paging request at virtual address dfff800000000001
>
> To make this easier to debug, this series makes the arm64 fault handling
> code log the corresponding memory range for potential shadow acceses,
> e.g.
>
> | Unable to handle kernel paging request at virtual address dfff800000000017
> | KASAN: null-ptr-deref in range [0x00000000000000b8-0x00000000000000bf]
>
> Since v1 [1]:
> * Use kasan_non_canonical_hook()
> * Drop move of kasan_shadow_to_mem()
> * Update commit messages
>
> [1] https://lore.kernel.org/r/20211202112731.3346975-1-mark.rutland@arm.com
>
> Thanks,
> Mark.
>
> Mark Rutland (2):
>   arm64: mm: use die_kernel_fault() in do_mem_abort()
>   arm64: mm: log potential KASAN shadow alias
>
>  arch/arm64/mm/fault.c | 9 ++++-----
>  1 file changed, 4 insertions(+), 5 deletions(-)
>
> --
> 2.30.2
>

Tested-by: Andrey Konovalov <andreyknvl@gmail.com>

Thanks, Mark!

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases
  2021-12-07 18:32 [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases Mark Rutland
                   ` (2 preceding siblings ...)
  2021-12-10 17:46 ` [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases Andrey Konovalov
@ 2021-12-13 18:24 ` Will Deacon
  2021-12-13 19:18 ` Catalin Marinas
  4 siblings, 0 replies; 6+ messages in thread
From: Will Deacon @ 2021-12-13 18:24 UTC (permalink / raw)
  To: Mark Rutland
  Cc: linux-arm-kernel, andreyknvl, catalin.marinas, dvyukov, glider,
	ryabinin.a.a

On Tue, Dec 07, 2021 at 06:32:24PM +0000, Mark Rutland wrote:
> When using KASAN_GENERIC or KASAN_SW_TAGS, many representable pointer
> values (e.g. NULL) don't have a legitimate shadow address. If KASAN
> instrumentation attempts to access the shadow for such pointers, it will
> fault on an unusual-looking address, e.g.
> 
> | Unable to handle kernel paging request at virtual address dfff800000000001
> 
> To make this easier to debug, this series makes the arm64 fault handling
> code log the corresponding memory range for potential shadow acceses,
> e.g.
> 
> | Unable to handle kernel paging request at virtual address dfff800000000017
> | KASAN: null-ptr-deref in range [0x00000000000000b8-0x00000000000000bf]

Cheers, that should help with debugging!

Acked-by: Will Deacon <will@kernel.org>

Will

_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases
  2021-12-07 18:32 [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases Mark Rutland
                   ` (3 preceding siblings ...)
  2021-12-13 18:24 ` Will Deacon
@ 2021-12-13 19:18 ` Catalin Marinas
  4 siblings, 0 replies; 6+ messages in thread
From: Catalin Marinas @ 2021-12-13 19:18 UTC (permalink / raw)
  To: Mark Rutland, linux-arm-kernel
  Cc: Will Deacon, ryabinin.a.a, andreyknvl, dvyukov, glider

On Tue, 7 Dec 2021 18:32:24 +0000, Mark Rutland wrote:
> When using KASAN_GENERIC or KASAN_SW_TAGS, many representable pointer
> values (e.g. NULL) don't have a legitimate shadow address. If KASAN
> instrumentation attempts to access the shadow for such pointers, it will
> fault on an unusual-looking address, e.g.
> 
> | Unable to handle kernel paging request at virtual address dfff800000000001
> 
> [...]

Applied to arm64 (for-next/kasan), thanks!

[1/2] arm64: mm: use die_kernel_fault() in do_mem_abort()
      https://git.kernel.org/arm64/c/6f6cfa586799
[2/2] arm64: mm: log potential KASAN shadow alias
      https://git.kernel.org/arm64/c/07b742a4d912

-- 
Catalin


_______________________________________________
linux-arm-kernel mailing list
linux-arm-kernel@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-arm-kernel

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2021-12-13 19:19 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-12-07 18:32 [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases Mark Rutland
2021-12-07 18:32 ` [PATCH v2 1/2] arm64: mm: use die_kernel_fault() in do_mem_abort() Mark Rutland
2021-12-07 18:32 ` [PATCH v2 2/2] arm64: mm: log potential KASAN shadow alias Mark Rutland
2021-12-10 17:46 ` [PATCH v2 0/2] arm64: kasan: log potential KASAN shadow aliases Andrey Konovalov
2021-12-13 18:24 ` Will Deacon
2021-12-13 19:18 ` Catalin Marinas

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).