2019-05-19 13:08:55 +01:00
// SPDX-License-Identifier: GPL-2.0-only
2009-02-06 21:50:39 +01:00
/*
* Stack trace management functions
*
2021-05-04 14:49:14 +02:00
* Copyright ( C ) 2009 - 2021 Helge Deller < deller @ gmx . de >
2009-02-06 21:50:39 +01:00
* based on arch / x86 / kernel / stacktrace . c by Ingo Molnar < mingo @ redhat . com >
* and parisc unwind functions by Randolph Chung < tausq @ debian . org >
*
* TODO : Userspace stacktrace ( CONFIG_USER_STACKTRACE_SUPPORT )
*/
2021-11-09 22:47:24 +01:00
# include <linux/kernel.h>
2009-02-06 21:50:39 +01:00
# include <linux/stacktrace.h>
# include <asm/unwind.h>
2021-05-04 14:49:14 +02:00
static void notrace walk_stackframe ( struct task_struct * task ,
struct pt_regs * regs , bool ( * fn ) ( void * , unsigned long ) , void * cookie )
2009-02-06 21:50:39 +01:00
{
struct unwind_frame_info info ;
2018-08-17 17:00:08 +02:00
unwind_frame_init_task ( & info , task , NULL ) ;
2021-05-04 14:49:14 +02:00
while ( 1 ) {
2009-02-06 21:50:39 +01:00
if ( unwind_once ( & info ) < 0 | | info . ip = = 0 )
break ;
if ( __kernel_text_address ( info . ip ) )
2021-05-04 14:49:14 +02:00
if ( ! fn ( cookie , info . ip ) )
break ;
2009-02-06 21:50:39 +01:00
}
}
2021-05-04 14:49:14 +02:00
void arch_stack_walk ( stack_trace_consume_fn consume_entry , void * cookie ,
struct task_struct * task , struct pt_regs * regs )
2009-02-06 21:50:39 +01:00
{
2021-05-04 14:49:14 +02:00
walk_stackframe ( task , regs , consume_entry , cookie ) ;
2009-02-06 21:50:39 +01:00
}
2021-05-04 14:49:14 +02:00
int arch_stack_walk_reliable ( stack_trace_consume_fn consume_entry , void * cookie ,
struct task_struct * task )
2009-02-06 21:50:39 +01:00
{
2021-05-04 14:49:14 +02:00
walk_stackframe ( task , NULL , consume_entry , cookie ) ;
return 1 ;
2009-02-06 21:50:39 +01:00
}