linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
@ 2025-08-18 13:07 Tengda Wu
  2025-08-20 21:36 ` Dave Hansen
                   ` (2 more replies)
  0 siblings, 3 replies; 12+ messages in thread
From: Tengda Wu @ 2025-08-18 13:07 UTC (permalink / raw)
  To: x86
  Cc: Andrey Ryabinin, Thomas Gleixner, Alexander Potapenko,
	Andrey Konovalov, Borislav Petkov, Dave Hansen, Dmitry Vyukov,
	Ingo Molnar, linux-kernel, Tengda Wu

When process A accesses process B's `regs` from stack memory through
__show_regs(), the stack of process B keeps changing during runtime.
This causes false positives like "stack out-of-bounds" [1] or
"out-of-bounds" [2] warnings when reading `regs` contents.

Add __no_sanitize_address attribute to __show_regs() to suppress these
false positives while maintaining the ability to debug register states
across processes.

[1] https://lore.kernel.org/all/000000000000cb8e3a05c4ed84bb@google.com/
[2] A similar KASAN report:
[332706.552324] BUG: KASAN: out-of-bounds in __show_regs+0x4b/0x340
[332706.552433] Read of size 8 at addr ffff88d24999fb20 by task sysrq_t_test.sh/3977032
[332706.552562]
[332706.552652] CPU: 36 PID: 3977032 Comm: sysrq_t_test.sh Kdump: loaded Not tainted 6.6.0+ #20
[332706.552783] Hardware name: Huawei RH2288H V3/BC11HGSA0, BIOS 3.35 10/20/2016
[332706.552906] Call Trace:
[332706.552998]  <TASK>
[332706.553089]  dump_stack_lvl+0x32/0x50
[332706.553193]  print_address_description.constprop.0+0x6b/0x3d0
[332706.553303]  print_report+0xbe/0x280
[332706.553409]  ? __virt_addr_valid+0xed/0x160
[332706.553512]  ? __show_regs+0x4b/0x340
[332706.553612]  kasan_report+0xa8/0xe0
[332706.553716]  ? __show_regs+0x4b/0x340
[332706.553816]  ? asm_exc_page_fault+0x22/0x30
[332706.553919]  __show_regs+0x4b/0x340
[332706.554021]  ? asm_exc_page_fault+0x22/0x30
[332706.554123]  show_trace_log_lvl+0x274/0x3b0
[332706.554229]  ? load_elf_binary+0xf6e/0x1610
[332706.554330]  ? rep_stos_alternative+0x40/0x80
[332706.554439]  sched_show_task+0x211/0x290
[332706.554544]  ? __pfx_sched_show_task+0x10/0x10
[332706.554648]  ? _find_next_bit+0x6/0xc0
[332706.554749]  ? _find_next_bit+0x37/0xc0
[332706.554852]  show_state_filter+0x72/0x130
[332706.554956]  sysrq_handle_showstate+0x7/0x10
[332706.555062]  __handle_sysrq+0x146/0x2d0
[332706.555165]  write_sysrq_trigger+0x2f/0x50
[332706.555270]  proc_reg_write+0xdd/0x140
[332706.555372]  vfs_write+0x1ff/0x5f0
[332706.555474]  ? __pfx_vfs_write+0x10/0x10
[332706.555576]  ? __pfx___handle_mm_fault+0x10/0x10
[332706.555682]  ? __fget_light+0x99/0xf0
[332706.555785]  ksys_write+0xb8/0x150
[332706.555887]  ? __pfx_ksys_write+0x10/0x10
[332706.555989]  ? ktime_get_coarse_real_ts64+0x4e/0x70
[332706.556094]  do_syscall_64+0x55/0x100
[332706.556196]  entry_SYSCALL_64_after_hwframe+0x78/0xe2

Fixes: 3b3fa11bc700 ("x86/dumpstack: Print any pt_regs found on the stack")
Signed-off-by: Tengda Wu <wutengda@huaweicloud.com>
---
 arch/x86/include/asm/kdebug.h | 2 +-
 arch/x86/kernel/process_32.c  | 1 +
 arch/x86/kernel/process_64.c  | 1 +
 3 files changed, 3 insertions(+), 1 deletion(-)

diff --git a/arch/x86/include/asm/kdebug.h b/arch/x86/include/asm/kdebug.h
index d1514e70477b..2e0570d75bbc 100644
--- a/arch/x86/include/asm/kdebug.h
+++ b/arch/x86/include/asm/kdebug.h
@@ -36,7 +36,7 @@ extern void die(const char *, struct pt_regs *,long);
 void die_addr(const char *str, struct pt_regs *regs, long err, long gp_addr);
 extern int __must_check __die(const char *, struct pt_regs *, long);
 extern void show_stack_regs(struct pt_regs *regs);
-extern void __show_regs(struct pt_regs *regs, enum show_regs_mode,
+extern void __no_sanitize_address __show_regs(struct pt_regs *regs, enum show_regs_mode,
 			const char *log_lvl);
 extern void show_iret_regs(struct pt_regs *regs, const char *log_lvl);
 extern unsigned long oops_begin(void);
diff --git a/arch/x86/kernel/process_32.c b/arch/x86/kernel/process_32.c
index 3ef15c2f152f..1b7ed4dee18b 100644
--- a/arch/x86/kernel/process_32.c
+++ b/arch/x86/kernel/process_32.c
@@ -56,6 +56,7 @@
 
 #include "process.h"
 
+__no_sanitize_address
 void __show_regs(struct pt_regs *regs, enum show_regs_mode mode,
 		 const char *log_lvl)
 {
diff --git a/arch/x86/kernel/process_64.c b/arch/x86/kernel/process_64.c
index 52a5c03c353c..921c96154ce3 100644
--- a/arch/x86/kernel/process_64.c
+++ b/arch/x86/kernel/process_64.c
@@ -66,6 +66,7 @@
 #include "process.h"
 
 /* Prints also some state that isn't saved in the pt_regs */
+__no_sanitize_address
 void __show_regs(struct pt_regs *regs, enum show_regs_mode mode,
 		 const char *log_lvl)
 {
-- 
2.34.1


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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-18 13:07 [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs() Tengda Wu
@ 2025-08-20 21:36 ` Dave Hansen
  2025-08-21  3:13   ` Tengda Wu
  2025-08-27 14:36 ` Dave Hansen
  2025-08-27 14:45 ` Andrey Ryabinin
  2 siblings, 1 reply; 12+ messages in thread
From: Dave Hansen @ 2025-08-20 21:36 UTC (permalink / raw)
  To: Tengda Wu, x86
  Cc: Andrey Ryabinin, Thomas Gleixner, Alexander Potapenko,
	Andrey Konovalov, Borislav Petkov, Dave Hansen, Dmitry Vyukov,
	Ingo Molnar, linux-kernel

On 8/18/25 06:07, Tengda Wu wrote:
> When process A accesses process B's `regs` from stack memory through
> __show_regs(), the stack of process B keeps changing during runtime.
> This causes false positives like "stack out-of-bounds" [1] or
> "out-of-bounds" [2] warnings when reading `regs` contents.

Could you explain a little bit more how you know that these are false
positives?

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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-20 21:36 ` Dave Hansen
@ 2025-08-21  3:13   ` Tengda Wu
  2025-08-27 11:58     ` Tengda Wu
  0 siblings, 1 reply; 12+ messages in thread
From: Tengda Wu @ 2025-08-21  3:13 UTC (permalink / raw)
  To: Dave Hansen, x86
  Cc: Andrey Ryabinin, Thomas Gleixner, Alexander Potapenko,
	Andrey Konovalov, Borislav Petkov, Dave Hansen, Dmitry Vyukov,
	Ingo Molnar, linux-kernel



On 2025/8/21 5:36, Dave Hansen wrote:
> On 8/18/25 06:07, Tengda Wu wrote:
>> When process A accesses process B's `regs` from stack memory through
>> __show_regs(), the stack of process B keeps changing during runtime.
>> This causes false positives like "stack out-of-bounds" [1] or
>> "out-of-bounds" [2] warnings when reading `regs` contents.
> 
> Could you explain a little bit more how you know that these are false
> positives?

Thanks for the question. We believe this is a false positive caused by a
race condition during asynchronous stack tracing of a running process:

Process A (stack trace all processes)         Process B (running)
1. echo t > /proc/sysrq-trigger

show_trace_log_lvl
  regs = unwind_get_entry_regs()
  show_regs_if_on_stack(regs)
                                              2. The stack data pointed by
                                                 `regs` keeps changing, and
                                                 so are the markings in its
                                                 KASAN shadow region.
    __show_regs(regs)
      regs->ax, regs->bx, ...
        3. hit KASAN redzones, OOB

When process A stacks process B without suspending it, the continuous
changes in process B's stack (and corresponding KASAN shadow markings)
may cause process A to hit KASAN redzones when accessing obsolete `regs`
addresses, resulting in false positive reports.

A sample error log for this scenario is shown below:

[332706.551830] task:cat             state:R  running task     stack:0     pid:3983623 ppid:3977902 flags:0x00004002
[332706.551847] Call Trace:
[332706.551853]  <TASK>
[332706.551860]  __schedule+0x809/0x1050
[332706.551873]  ? __pfx___schedule+0x10/0x10
[332706.551885]  ? __stack_depot_save+0x34/0x340
[332706.551899]  schedule+0x82/0x160
[332706.551911]  io_schedule+0x68/0xa0
[332706.551923]  __folio_lock_killable+0x1db/0x410
[332706.551940]  ? __pfx___folio_lock_killable+0x10/0x10
[332706.551955]  ? __pfx_wake_page_function+0x10/0x10
[332706.551969]  ? __filemap_get_folio+0x4b/0x3d0
[332706.551982]  filemap_fault+0x67a/0xbd0
[332706.551996]  ? __pfx_filemap_fault+0x10/0x10
[332706.552008]  ? policy_node+0x8a/0xa0
[332706.552021]  ? __mod_node_page_state+0x23/0xf0
[332706.552035]  __do_fault+0x6d/0x340
[332706.552048]  do_cow_fault+0xdd/0x300
[332706.552061]  do_fault+0x141/0x1e0
[332706.552074]  __handle_mm_fault+0x839/0xa70
[332706.552089]  ? __pfx___handle_mm_fault+0x10/0x10
[332706.552105]  ? find_vma+0x6a/0x90
[332706.552117]  handle_mm_fault+0x27d/0x470
[332706.552132]  exc_page_fault+0x336/0x6d0
[332706.552145]  asm_exc_page_fault+0x22/0x30
[332706.552157] RIP: 0010:rep_stos_alternative+0x40/0x80                                         --- (1)
[332706.552173] Code: Unable to access opcode bytes at 0x7ffe929c4fd6.                           --- (2)
[332706.552181] RSP: 3fa6:ffff88ba5e554200 EFLAGS: ffffffff9d50c0e0 ORIG_RAX: ffff88ba5e554200   --- (3)
[332706.552195] ==================================================================
[332706.552324] BUG: KASAN: out-of-bounds in __show_regs+0x4b/0x340                              --- (4)
[332706.552433] Read of size 8 at addr ffff88d24999fb20 by task sysrq_t_test.sh/3977032

We focus on logs (1) to (4):
 * Log (1) shows the current regs->ip (a kernel-mode address);
 * Log (2) displays regs->ip - PROLOGUE_SIZE, which deviates significantly
   from kernel-mode addresses, indicating regs->ip has changed.
 * Log (3) then reveals anomalous values in regs->{ss,sp,flags}.
 * Finally, Log (4) reports a KASAN OOB error when accessing regs->bx.

Stack tracing a running task cannot guarantee the accuracy of the printed
regs values, but accessing regs addresses does not cause kernel instability.
Similar cases have been consistently handled this way in the past. [1][2]
We therefore consider this a KASAN false positive.

[1] https://lore.kernel.org/all/20220915150417.722975-40-glider@google.com/T/#u
[2] https://lore.kernel.org/all/5f6e80c4b0c7f7f0b6211900847a247cdaad753c.1479398226.git.jpoimboe@redhat.com/T/#u


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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-21  3:13   ` Tengda Wu
@ 2025-08-27 11:58     ` Tengda Wu
  0 siblings, 0 replies; 12+ messages in thread
From: Tengda Wu @ 2025-08-27 11:58 UTC (permalink / raw)
  To: Dave Hansen, Alexander Potapenko
  Cc: Andrey Ryabinin, Thomas Gleixner, Andrey Konovalov,
	Borislav Petkov, Dave Hansen, Dmitry Vyukov, Ingo Molnar,
	linux-kernel, x86


On 2025/8/21 11:13, Tengda Wu wrote:
> 
> 
> On 2025/8/21 5:36, Dave Hansen wrote:
>> On 8/18/25 06:07, Tengda Wu wrote:
>>> When process A accesses process B's `regs` from stack memory through
>>> __show_regs(), the stack of process B keeps changing during runtime.
>>> This causes false positives like "stack out-of-bounds" [1] or
>>> "out-of-bounds" [2] warnings when reading `regs` contents.
>>
>> Could you explain a little bit more how you know that these are false
>> positives?
> 
> Thanks for the question. We believe this is a false positive caused by a
> race condition during asynchronous stack tracing of a running process:
> 
> Process A (stack trace all processes)         Process B (running)
> 1. echo t > /proc/sysrq-trigger
> 
> show_trace_log_lvl
>   regs = unwind_get_entry_regs()
>   show_regs_if_on_stack(regs)
>                                               2. The stack data pointed by
>                                                  `regs` keeps changing, and
>                                                  so are the markings in its
>                                                  KASAN shadow region.
>     __show_regs(regs)
>       regs->ax, regs->bx, ...
>         3. hit KASAN redzones, OOB
> 
> When process A stacks process B without suspending it, the continuous
> changes in process B's stack (and corresponding KASAN shadow markings)
> may cause process A to hit KASAN redzones when accessing obsolete `regs`
> addresses, resulting in false positive reports.
> 
> A sample error log for this scenario is shown below:
> 
> [332706.551830] task:cat             state:R  running task     stack:0     pid:3983623 ppid:3977902 flags:0x00004002
> [332706.551847] Call Trace:
> [332706.551853]  <TASK>
> [332706.551860]  __schedule+0x809/0x1050
> [332706.551873]  ? __pfx___schedule+0x10/0x10
> [332706.551885]  ? __stack_depot_save+0x34/0x340
> [332706.551899]  schedule+0x82/0x160
> [332706.551911]  io_schedule+0x68/0xa0
> [332706.551923]  __folio_lock_killable+0x1db/0x410
> [332706.551940]  ? __pfx___folio_lock_killable+0x10/0x10
> [332706.551955]  ? __pfx_wake_page_function+0x10/0x10
> [332706.551969]  ? __filemap_get_folio+0x4b/0x3d0
> [332706.551982]  filemap_fault+0x67a/0xbd0
> [332706.551996]  ? __pfx_filemap_fault+0x10/0x10
> [332706.552008]  ? policy_node+0x8a/0xa0
> [332706.552021]  ? __mod_node_page_state+0x23/0xf0
> [332706.552035]  __do_fault+0x6d/0x340
> [332706.552048]  do_cow_fault+0xdd/0x300
> [332706.552061]  do_fault+0x141/0x1e0
> [332706.552074]  __handle_mm_fault+0x839/0xa70
> [332706.552089]  ? __pfx___handle_mm_fault+0x10/0x10
> [332706.552105]  ? find_vma+0x6a/0x90
> [332706.552117]  handle_mm_fault+0x27d/0x470
> [332706.552132]  exc_page_fault+0x336/0x6d0
> [332706.552145]  asm_exc_page_fault+0x22/0x30
> [332706.552157] RIP: 0010:rep_stos_alternative+0x40/0x80                                         --- (1)
> [332706.552173] Code: Unable to access opcode bytes at 0x7ffe929c4fd6.                           --- (2)
> [332706.552181] RSP: 3fa6:ffff88ba5e554200 EFLAGS: ffffffff9d50c0e0 ORIG_RAX: ffff88ba5e554200   --- (3)
> [332706.552195] ==================================================================
> [332706.552324] BUG: KASAN: out-of-bounds in __show_regs+0x4b/0x340                              --- (4)
> [332706.552433] Read of size 8 at addr ffff88d24999fb20 by task sysrq_t_test.sh/3977032
> 
> We focus on logs (1) to (4):
>  * Log (1) shows the current regs->ip (a kernel-mode address);
>  * Log (2) displays regs->ip - PROLOGUE_SIZE, which deviates significantly
>    from kernel-mode addresses, indicating regs->ip has changed.
>  * Log (3) then reveals anomalous values in regs->{ss,sp,flags}.
>  * Finally, Log (4) reports a KASAN OOB error when accessing regs->bx.
> 
> Stack tracing a running task cannot guarantee the accuracy of the printed
> regs values, but accessing regs addresses does not cause kernel instability.
> Similar cases have been consistently handled this way in the past. [1][2]
> We therefore consider this a KASAN false positive.
> 
> [1] https://lore.kernel.org/all/20220915150417.722975-40-glider@google.com/T/#u
> [2] https://lore.kernel.org/all/5f6e80c4b0c7f7f0b6211900847a247cdaad753c.1479398226.git.jpoimboe@redhat.com/T/#u

Gentle ping. 
Any comment or suggestion is appreciated.

Thanks,
Tengda


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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-18 13:07 [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs() Tengda Wu
  2025-08-20 21:36 ` Dave Hansen
@ 2025-08-27 14:36 ` Dave Hansen
  2025-08-28 12:04   ` Tengda Wu
  2025-08-27 14:45 ` Andrey Ryabinin
  2 siblings, 1 reply; 12+ messages in thread
From: Dave Hansen @ 2025-08-27 14:36 UTC (permalink / raw)
  To: Tengda Wu, x86
  Cc: Andrey Ryabinin, Thomas Gleixner, Alexander Potapenko,
	Andrey Konovalov, Borislav Petkov, Dave Hansen, Dmitry Vyukov,
	Ingo Molnar, linux-kernel, Peter Zijlstra, Josh Poimboeuf

On 8/18/25 06:07, Tengda Wu wrote:
> +__no_sanitize_address
>  void __show_regs(struct pt_regs *regs, enum show_regs_mode mode,
>  		 const char *log_lvl)

I'd feel a lot better about this if it didn't just disable KASAN for the
whole function. Surely there are other __show_regs() users that could
benefit from sanitizer coverage.

Can we limit the impact to just the asynchronous (unsafe) stack walkers?
If it's just for sysrq, this seems like the kind of thing we could just
a flag somewhere and have KASAN suppress the warning. Or to generically
tell KASAN that we might be doing accesses in a certain memory range
that are unsafe.

I'm also adding Peter and Josh to cc. Seems like the kind of thing they
might have an opinion on.

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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-18 13:07 [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs() Tengda Wu
  2025-08-20 21:36 ` Dave Hansen
  2025-08-27 14:36 ` Dave Hansen
@ 2025-08-27 14:45 ` Andrey Ryabinin
  2025-08-28 12:06   ` Tengda Wu
  2 siblings, 1 reply; 12+ messages in thread
From: Andrey Ryabinin @ 2025-08-27 14:45 UTC (permalink / raw)
  To: Tengda Wu, x86
  Cc: Thomas Gleixner, Alexander Potapenko, Andrey Konovalov,
	Borislav Petkov, Dave Hansen, Dmitry Vyukov, Ingo Molnar,
	linux-kernel, Peter Zijlstra, Josh Poimboeuf



On 8/18/25 3:07 PM, Tengda Wu wrote:
> When process A accesses process B's `regs` from stack memory through
> __show_regs(), the stack of process B keeps changing during runtime.
> This causes false positives like "stack out-of-bounds" [1] or
> "out-of-bounds" [2] warnings when reading `regs` contents.
> 
> Add __no_sanitize_address attribute to __show_regs() to suppress these
> false positives while maintaining the ability to debug register states
> across processes.
> 
> [1] https://lore.kernel.org/all/000000000000cb8e3a05c4ed84bb@google.com/
> [2] A similar KASAN report:
> [332706.552324] BUG: KASAN: out-of-bounds in __show_regs+0x4b/0x340
> [332706.552433] Read of size 8 at addr ffff88d24999fb20 by task sysrq_t_test.sh/3977032
> [332706.552562]
> [332706.552652] CPU: 36 PID: 3977032 Comm: sysrq_t_test.sh Kdump: loaded Not tainted 6.6.0+ #20
> [332706.552783] Hardware name: Huawei RH2288H V3/BC11HGSA0, BIOS 3.35 10/20/2016
> [332706.552906] Call Trace:
> [332706.552998]  <TASK>
> [332706.553089]  dump_stack_lvl+0x32/0x50
> [332706.553193]  print_address_description.constprop.0+0x6b/0x3d0
> [332706.553303]  print_report+0xbe/0x280
> [332706.553409]  ? __virt_addr_valid+0xed/0x160
> [332706.553512]  ? __show_regs+0x4b/0x340
> [332706.553612]  kasan_report+0xa8/0xe0
> [332706.553716]  ? __show_regs+0x4b/0x340
> [332706.553816]  ? asm_exc_page_fault+0x22/0x30
> [332706.553919]  __show_regs+0x4b/0x340
> [332706.554021]  ? asm_exc_page_fault+0x22/0x30
> [332706.554123]  show_trace_log_lvl+0x274/0x3b0
> [332706.554229]  ? load_elf_binary+0xf6e/0x1610
> [332706.554330]  ? rep_stos_alternative+0x40/0x80
> [332706.554439]  sched_show_task+0x211/0x290
> [332706.554544]  ? __pfx_sched_show_task+0x10/0x10
> [332706.554648]  ? _find_next_bit+0x6/0xc0
> [332706.554749]  ? _find_next_bit+0x37/0xc0
> [332706.554852]  show_state_filter+0x72/0x130
> [332706.554956]  sysrq_handle_showstate+0x7/0x10
> [332706.555062]  __handle_sysrq+0x146/0x2d0
> [332706.555165]  write_sysrq_trigger+0x2f/0x50
> [332706.555270]  proc_reg_write+0xdd/0x140
> [332706.555372]  vfs_write+0x1ff/0x5f0
> [332706.555474]  ? __pfx_vfs_write+0x10/0x10
> [332706.555576]  ? __pfx___handle_mm_fault+0x10/0x10
> [332706.555682]  ? __fget_light+0x99/0xf0
> [332706.555785]  ksys_write+0xb8/0x150
> [332706.555887]  ? __pfx_ksys_write+0x10/0x10
> [332706.555989]  ? ktime_get_coarse_real_ts64+0x4e/0x70
> [332706.556094]  do_syscall_64+0x55/0x100
> [332706.556196]  entry_SYSCALL_64_after_hwframe+0x78/0xe2
> 
> Fixes: 3b3fa11bc700 ("x86/dumpstack: Print any pt_regs found on the stack")
> Signed-off-by: Tengda Wu <wutengda@huaweicloud.com>
> ---
>  arch/x86/include/asm/kdebug.h | 2 +-
>  arch/x86/kernel/process_32.c  | 1 +
>  arch/x86/kernel/process_64.c  | 1 +
>  3 files changed, 3 insertions(+), 1 deletion(-)
> 
> diff --git a/arch/x86/include/asm/kdebug.h b/arch/x86/include/asm/kdebug.h
> index d1514e70477b..2e0570d75bbc 100644
> --- a/arch/x86/include/asm/kdebug.h
> +++ b/arch/x86/include/asm/kdebug.h
> @@ -36,7 +36,7 @@ extern void die(const char *, struct pt_regs *,long);
>  void die_addr(const char *str, struct pt_regs *regs, long err, long gp_addr);
>  extern int __must_check __die(const char *, struct pt_regs *, long);
>  extern void show_stack_regs(struct pt_regs *regs);
> -extern void __show_regs(struct pt_regs *regs, enum show_regs_mode,
> +extern void __no_sanitize_address __show_regs(struct pt_regs *regs, enum show_regs_mode,
>  			const char *log_lvl);
>  extern void show_iret_regs(struct pt_regs *regs, const char *log_lvl);
>  extern unsigned long oops_begin(void);
> diff --git a/arch/x86/kernel/process_32.c b/arch/x86/kernel/process_32.c
> index 3ef15c2f152f..1b7ed4dee18b 100644
> --- a/arch/x86/kernel/process_32.c
> +++ b/arch/x86/kernel/process_32.c
> @@ -56,6 +56,7 @@
>  
>  #include "process.h"
>  
> +__no_sanitize_address
>  void __show_regs(struct pt_regs *regs, enum show_regs_mode mode,
>  		 const char *log_lvl)
>  {
> diff --git a/arch/x86/kernel/process_64.c b/arch/x86/kernel/process_64.c
> index 52a5c03c353c..921c96154ce3 100644
> --- a/arch/x86/kernel/process_64.c
> +++ b/arch/x86/kernel/process_64.c
> @@ -66,6 +66,7 @@
>  #include "process.h"
>  
>  /* Prints also some state that isn't saved in the pt_regs */
> +__no_sanitize_address
>  void __show_regs(struct pt_regs *regs, enum show_regs_mode mode,
>  		 const char *log_lvl)
>  {


__no_sanitize_address affects only __show_regs() function.
But the `regs` are passed down in show_iret_regs()->show_ip()->show_opcodes()
and all these also accesses `regs`

I see several options here:

1. Use kasan_disable_current()/kasan_enable_current() to wrap code accessing `regs`.
And maybe something like:
         if (!on_current_stack(regs))
                 kasan_disable_current();

so we skip kasan reports only if `regs` belong to other task.

2. Sprinkle over __no_sanitize_address all functions accessing `regs`.
But this disable all memory access checks all the time in these functions.

3. Use READ_ONCE_NOCHECK() to read regs->

4. Introduce memcpy_no_sanitize_address(), and use it to copy snapshot of `regs`
somewhere (on the stack of current task ?). But pt_regs is 168 bytes, I'm not sure if this
is acceptable stack usage increment.

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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-27 14:36 ` Dave Hansen
@ 2025-08-28 12:04   ` Tengda Wu
  0 siblings, 0 replies; 12+ messages in thread
From: Tengda Wu @ 2025-08-28 12:04 UTC (permalink / raw)
  To: Dave Hansen, x86
  Cc: Andrey Ryabinin, Thomas Gleixner, Alexander Potapenko,
	Andrey Konovalov, Borislav Petkov, Dave Hansen, Dmitry Vyukov,
	Ingo Molnar, linux-kernel, Peter Zijlstra, Josh Poimboeuf



On 2025/8/27 22:36, Dave Hansen wrote:
> On 8/18/25 06:07, Tengda Wu wrote:
>> +__no_sanitize_address
>>  void __show_regs(struct pt_regs *regs, enum show_regs_mode mode,
>>  		 const char *log_lvl)
> 
> I'd feel a lot better about this if it didn't just disable KASAN for the
> whole function. Surely there are other __show_regs() users that could
> benefit from sanitizer coverage.
> 
> Can we limit the impact to just the asynchronous (unsafe) stack walkers?
> If it's just for sysrq, this seems like the kind of thing we could just
> a flag somewhere and have KASAN suppress the warning. Or to generically
> tell KASAN that we might be doing accesses in a certain memory range
> that are unsafe.
> 
> I'm also adding Peter and Josh to cc. Seems like the kind of thing they
> might have an opinion on.

I see what you mean. Andrey has provided several approaches — perhaps we
can make a selection from those.


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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-27 14:45 ` Andrey Ryabinin
@ 2025-08-28 12:06   ` Tengda Wu
  2025-08-28 14:13     ` Dave Hansen
  2025-08-28 19:16     ` Josh Poimboeuf
  0 siblings, 2 replies; 12+ messages in thread
From: Tengda Wu @ 2025-08-28 12:06 UTC (permalink / raw)
  To: Andrey Ryabinin, x86
  Cc: Thomas Gleixner, Alexander Potapenko, Andrey Konovalov,
	Borislav Petkov, Dave Hansen, Dmitry Vyukov, Ingo Molnar,
	linux-kernel, Peter Zijlstra, Josh Poimboeuf


Hi Andrey,

On 2025/8/27 22:45, Andrey Ryabinin wrote:
> 
> 
> On 8/18/25 3:07 PM, Tengda Wu wrote:
>> When process A accesses process B's `regs` from stack memory through
>> __show_regs(), the stack of process B keeps changing during runtime.
>> This causes false positives like "stack out-of-bounds" [1] or
>> "out-of-bounds" [2] warnings when reading `regs` contents.
>>
>> Add __no_sanitize_address attribute to __show_regs() to suppress these
>> false positives while maintaining the ability to debug register states
>> across processes.
>>
>> [1] https://lore.kernel.org/all/000000000000cb8e3a05c4ed84bb@google.com/
>> [2] A similar KASAN report:
>> [332706.552324] BUG: KASAN: out-of-bounds in __show_regs+0x4b/0x340
>> [332706.552433] Read of size 8 at addr ffff88d24999fb20 by task sysrq_t_test.sh/3977032
>> [332706.552562]
>> [332706.552652] CPU: 36 PID: 3977032 Comm: sysrq_t_test.sh Kdump: loaded Not tainted 6.6.0+ #20
>> [332706.552783] Hardware name: Huawei RH2288H V3/BC11HGSA0, BIOS 3.35 10/20/2016
>> [332706.552906] Call Trace:
>> [332706.552998]  <TASK>
>> [332706.553089]  dump_stack_lvl+0x32/0x50
>> [332706.553193]  print_address_description.constprop.0+0x6b/0x3d0
>> [332706.553303]  print_report+0xbe/0x280
>> [332706.553409]  ? __virt_addr_valid+0xed/0x160
>> [332706.553512]  ? __show_regs+0x4b/0x340
>> [332706.553612]  kasan_report+0xa8/0xe0
>> [332706.553716]  ? __show_regs+0x4b/0x340
>> [332706.553816]  ? asm_exc_page_fault+0x22/0x30
>> [332706.553919]  __show_regs+0x4b/0x340
>> [332706.554021]  ? asm_exc_page_fault+0x22/0x30
>> [332706.554123]  show_trace_log_lvl+0x274/0x3b0
>> [332706.554229]  ? load_elf_binary+0xf6e/0x1610
>> [332706.554330]  ? rep_stos_alternative+0x40/0x80
>> [332706.554439]  sched_show_task+0x211/0x290
>> [332706.554544]  ? __pfx_sched_show_task+0x10/0x10
>> [332706.554648]  ? _find_next_bit+0x6/0xc0
>> [332706.554749]  ? _find_next_bit+0x37/0xc0
>> [332706.554852]  show_state_filter+0x72/0x130
>> [332706.554956]  sysrq_handle_showstate+0x7/0x10
>> [332706.555062]  __handle_sysrq+0x146/0x2d0
>> [332706.555165]  write_sysrq_trigger+0x2f/0x50
>> [332706.555270]  proc_reg_write+0xdd/0x140
>> [332706.555372]  vfs_write+0x1ff/0x5f0
>> [332706.555474]  ? __pfx_vfs_write+0x10/0x10
>> [332706.555576]  ? __pfx___handle_mm_fault+0x10/0x10
>> [332706.555682]  ? __fget_light+0x99/0xf0
>> [332706.555785]  ksys_write+0xb8/0x150
>> [332706.555887]  ? __pfx_ksys_write+0x10/0x10
>> [332706.555989]  ? ktime_get_coarse_real_ts64+0x4e/0x70
>> [332706.556094]  do_syscall_64+0x55/0x100
>> [332706.556196]  entry_SYSCALL_64_after_hwframe+0x78/0xe2
>>
>> Fixes: 3b3fa11bc700 ("x86/dumpstack: Print any pt_regs found on the stack")
>> Signed-off-by: Tengda Wu <wutengda@huaweicloud.com>
>> ---
>>  arch/x86/include/asm/kdebug.h | 2 +-
>>  arch/x86/kernel/process_32.c  | 1 +
>>  arch/x86/kernel/process_64.c  | 1 +
>>  3 files changed, 3 insertions(+), 1 deletion(-)
>>
>> diff --git a/arch/x86/include/asm/kdebug.h b/arch/x86/include/asm/kdebug.h
>> index d1514e70477b..2e0570d75bbc 100644
>> --- a/arch/x86/include/asm/kdebug.h
>> +++ b/arch/x86/include/asm/kdebug.h
>> @@ -36,7 +36,7 @@ extern void die(const char *, struct pt_regs *,long);
>>  void die_addr(const char *str, struct pt_regs *regs, long err, long gp_addr);
>>  extern int __must_check __die(const char *, struct pt_regs *, long);
>>  extern void show_stack_regs(struct pt_regs *regs);
>> -extern void __show_regs(struct pt_regs *regs, enum show_regs_mode,
>> +extern void __no_sanitize_address __show_regs(struct pt_regs *regs, enum show_regs_mode,
>>  			const char *log_lvl);
>>  extern void show_iret_regs(struct pt_regs *regs, const char *log_lvl);
>>  extern unsigned long oops_begin(void);
>> diff --git a/arch/x86/kernel/process_32.c b/arch/x86/kernel/process_32.c
>> index 3ef15c2f152f..1b7ed4dee18b 100644
>> --- a/arch/x86/kernel/process_32.c
>> +++ b/arch/x86/kernel/process_32.c
>> @@ -56,6 +56,7 @@
>>  
>>  #include "process.h"
>>  
>> +__no_sanitize_address
>>  void __show_regs(struct pt_regs *regs, enum show_regs_mode mode,
>>  		 const char *log_lvl)
>>  {
>> diff --git a/arch/x86/kernel/process_64.c b/arch/x86/kernel/process_64.c
>> index 52a5c03c353c..921c96154ce3 100644
>> --- a/arch/x86/kernel/process_64.c
>> +++ b/arch/x86/kernel/process_64.c
>> @@ -66,6 +66,7 @@
>>  #include "process.h"
>>  
>>  /* Prints also some state that isn't saved in the pt_regs */
>> +__no_sanitize_address
>>  void __show_regs(struct pt_regs *regs, enum show_regs_mode mode,
>>  		 const char *log_lvl)
>>  {
> 
> 
> __no_sanitize_address affects only __show_regs() function.
> But the `regs` are passed down in show_iret_regs()->show_ip()->show_opcodes()
> and all these also accesses `regs`

Indeed. Thanks for pointing that out.

> 
> I see several options here:
> 
> 1. Use kasan_disable_current()/kasan_enable_current() to wrap code accessing `regs`.
> And maybe something like:
>          if (!on_current_stack(regs))
>                  kasan_disable_current();
> 
> so we skip kasan reports only if `regs` belong to other task.

This looks like the best fit.

> 
> 2. Sprinkle over __no_sanitize_address all functions accessing `regs`.
> But this disable all memory access checks all the time in these functions.
> 

As Dave said, this does not provide finer-grained control than Option 1.

> 3. Use READ_ONCE_NOCHECK() to read regs->

This might affect code readability, as there are too many `regs->xxx`
inside these functions.

> 
> 4. Introduce memcpy_no_sanitize_address(), and use it to copy snapshot of `regs`
> somewhere (on the stack of current task ?). But pt_regs is 168 bytes, I'm not sure if this
> is acceptable stack usage increment.

This sounds a bit complicated.


So, for Option 1:

It seems there's no existing on_current_stack function available.
Implementing an on_current_stack function would be somewhat
challenging for me. 

How about just check the task directly inside show_trace_log_lvl?
I've traced all kernel paths calling __show_regs() and found that
asynchronous stack walkers always reaches here. — seems suitable?

Here is a sample patch:

diff --git a/arch/x86/kernel/dumpstack.c b/arch/x86/kernel/dumpstack.c
index 71ee20102a8a..e519aeb00705 100644
--- a/arch/x86/kernel/dumpstack.c
+++ b/arch/x86/kernel/dumpstack.c
@@ -189,9 +189,15 @@ static void show_trace_log_lvl(struct task_struct *task, struct pt_regs *regs,
        unsigned long visit_mask = 0;
        int graph_idx = 0;
        bool partial = false;
+       bool kasan_disabled = false;
 
        printk("%sCall Trace:\n", log_lvl);
 
+       if (task != current) {
+               kasan_disable_current();
+               kasan_disabled = true;
+       }
+
        unwind_start(&state, task, regs, stack);
        stack = stack ?: get_stack_pointer(task, regs);
        regs = unwind_get_entry_regs(&state, &partial);
@@ -301,6 +307,9 @@ static void show_trace_log_lvl(struct task_struct *task, struct pt_regs *regs,
                if (stack_name)
                        printk("%s </%s>\n", log_lvl, stack_name);
        }
+
+       if (kasan_disabled)
+               kasan_enable_current();
 }


Best regards,
Tengda


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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-28 12:06   ` Tengda Wu
@ 2025-08-28 14:13     ` Dave Hansen
  2025-08-29  2:50       ` Tengda Wu
  2025-08-28 19:16     ` Josh Poimboeuf
  1 sibling, 1 reply; 12+ messages in thread
From: Dave Hansen @ 2025-08-28 14:13 UTC (permalink / raw)
  To: Tengda Wu, Andrey Ryabinin, x86
  Cc: Thomas Gleixner, Alexander Potapenko, Andrey Konovalov,
	Borislav Petkov, Dave Hansen, Dmitry Vyukov, Ingo Molnar,
	linux-kernel, Peter Zijlstra, Josh Poimboeuf

On 8/28/25 05:06, Tengda Wu wrote:
> It seems there's no existing on_current_stack function available.
> Implementing an on_current_stack function would be somewhat
> challenging for me. 

Is there some reason that object_is_on_stack() won't work?

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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-28 12:06   ` Tengda Wu
  2025-08-28 14:13     ` Dave Hansen
@ 2025-08-28 19:16     ` Josh Poimboeuf
  2025-08-29  9:45       ` Tengda Wu
  1 sibling, 1 reply; 12+ messages in thread
From: Josh Poimboeuf @ 2025-08-28 19:16 UTC (permalink / raw)
  To: Tengda Wu
  Cc: Andrey Ryabinin, x86, Thomas Gleixner, Alexander Potapenko,
	Andrey Konovalov, Borislav Petkov, Dave Hansen, Dmitry Vyukov,
	Ingo Molnar, linux-kernel, Peter Zijlstra

On Thu, Aug 28, 2025 at 08:06:17PM +0800, Tengda Wu wrote:
> +++ b/arch/x86/kernel/dumpstack.c
> @@ -189,9 +189,15 @@ static void show_trace_log_lvl(struct task_struct *task, struct pt_regs *regs,
>         unsigned long visit_mask = 0;
>         int graph_idx = 0;
>         bool partial = false;
> +       bool kasan_disabled = false;
>  
>         printk("%sCall Trace:\n", log_lvl);
>  
> +       if (task != current) {
> +               kasan_disable_current();
> +               kasan_disabled = true;
> +       }

Looks reasonable to me, though note that some callers pass a NULL @task
to indicate 'current'.

(No idea why, that subtlety should probably be removed...)

So this might need to be

	if (task && task != current) {
		...

-- 
Josh

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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-28 14:13     ` Dave Hansen
@ 2025-08-29  2:50       ` Tengda Wu
  0 siblings, 0 replies; 12+ messages in thread
From: Tengda Wu @ 2025-08-29  2:50 UTC (permalink / raw)
  To: Dave Hansen, Andrey Ryabinin, x86
  Cc: Thomas Gleixner, Alexander Potapenko, Andrey Konovalov,
	Borislav Petkov, Dave Hansen, Dmitry Vyukov, Ingo Molnar,
	linux-kernel, Peter Zijlstra, Josh Poimboeuf



On 2025/8/28 22:13, Dave Hansen wrote:
> On 8/28/25 05:06, Tengda Wu wrote:
>> It seems there's no existing on_current_stack function available.
>> Implementing an on_current_stack function would be somewhat
>> challenging for me. 
> 
> Is there some reason that object_is_on_stack() won't work?

Ah, that's what it's called! Yes, object_is_on_stack() should work
perfectly for that. Thanks for the clarification.

-- Tengda


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

* Re: [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs()
  2025-08-28 19:16     ` Josh Poimboeuf
@ 2025-08-29  9:45       ` Tengda Wu
  0 siblings, 0 replies; 12+ messages in thread
From: Tengda Wu @ 2025-08-29  9:45 UTC (permalink / raw)
  To: Josh Poimboeuf
  Cc: Andrey Ryabinin, x86, Thomas Gleixner, Alexander Potapenko,
	Andrey Konovalov, Borislav Petkov, Dave Hansen, Dmitry Vyukov,
	Ingo Molnar, linux-kernel, Peter Zijlstra



On 2025/8/29 3:16, Josh Poimboeuf wrote:
> On Thu, Aug 28, 2025 at 08:06:17PM +0800, Tengda Wu wrote:
>> +++ b/arch/x86/kernel/dumpstack.c
>> @@ -189,9 +189,15 @@ static void show_trace_log_lvl(struct task_struct *task, struct pt_regs *regs,
>>         unsigned long visit_mask = 0;
>>         int graph_idx = 0;
>>         bool partial = false;
>> +       bool kasan_disabled = false;
>>  
>>         printk("%sCall Trace:\n", log_lvl);
>>  
>> +       if (task != current) {
>> +               kasan_disable_current();
>> +               kasan_disabled = true;
>> +       }
> 
> Looks reasonable to me, though note that some callers pass a NULL @task
> to indicate 'current'.
> 
> (No idea why, that subtlety should probably be removed...)
> 
> So this might need to be
> 
> 	if (task && task != current) {
> 		...
> 

Dave mentioned that there's an object_is_on_stack available, which is
essentially on_current_stack. I will try using it and send out v2.

Thanks,
Tengda


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

end of thread, other threads:[~2025-08-29  9:45 UTC | newest]

Thread overview: 12+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-08-18 13:07 [PATCH -next] x86: Prevent KASAN false positive warnings in __show_regs() Tengda Wu
2025-08-20 21:36 ` Dave Hansen
2025-08-21  3:13   ` Tengda Wu
2025-08-27 11:58     ` Tengda Wu
2025-08-27 14:36 ` Dave Hansen
2025-08-28 12:04   ` Tengda Wu
2025-08-27 14:45 ` Andrey Ryabinin
2025-08-28 12:06   ` Tengda Wu
2025-08-28 14:13     ` Dave Hansen
2025-08-29  2:50       ` Tengda Wu
2025-08-28 19:16     ` Josh Poimboeuf
2025-08-29  9:45       ` Tengda Wu

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