int do_backtrace()
{
unw_cursor_t cursor;
unw_context_t context;
unw_getcontext(&context);
unw_init_local(&cursor, &context);
char buf[2048+1];
int len = 0;
memset(buf, 0, sizeof(buf));
int n=0;
while ( unw_step(&cursor) ) {
unw_word_t ip, sp, off;
unw_get_reg(&cursor, UNW_REG_IP, &ip);
unw_get_reg(&cursor, UNW_REG_SP, &sp);
char symbol[256] = {0};
unw_get_proc_name(&cursor, symbol, sizeof(symbol), &off);
strcat(buf, symbol);
strcat(buf, "\n");
// printf("#%-2d 0x%016" PRIxPTR " sp=0x%016" PRIxPTR " %s + 0x%" PRIxPTR "\n",
// ++n, ip, sp, symbol, off);
}
u_int32_t fd;
fd = open("/tmp/unwind.txt", O_CREAT|O_RDWR);
if(fd != -1)
{
write(fd, buf, 2048);
}
close(fd);
return len;
}
int fac()
{
char *pStr= NULL;
memcpy(pStr, "Hello", strlen("Hello"));
return 1;
}
int test()
{
fac();
return 1;
}
void exception_default_handler(int signo, siginfo_t *info, void *context)
{
do_backtrace();
exit(1);
}
#define SETSIG(sa, sig, func) \
{ memset( &sa, 0, sizeof( struct sigaction ) ); \
sa.sa_sigaction = func; \
sa.sa_flags = SA_RESTART | SA_SIGINFO; \
sigaction(sig, &sa, 0L); \
}
int main()
{
struct sigaction sa;
SETSIG(sa, SIGINT, exception_default_handler);
SETSIG(sa, SIGSEGV, exception_default_handler);
SETSIG(sa, SIGILL, exception_default_handler);
SETSIG(sa, SIGBUS, exception_default_handler);
SETSIG(sa, SIGQUIT, exception_default_handler);
SETSIG(sa, SIGFPE, exception_default_handler);
test();
return 0;
}
cat /tmp/unwind.txt
_Z25exception_default_handleriP9siginfo_tPv
sigwaitinfo
_Z4testv
main
libc_start_main_stage2
Above is my code. When I execute the program, the output is as below, why the backtrace is stopped at the function 'test'?
in my view, it should be stopped at the function 'fac' at leat. it is highly expected at 'memcpy'.
I searched many webpage through google and still have no idea. Could you please help to give some suggestions? Thank you very much!
I have tried to modify the code and add more depth function call levels.
I found the output backtrace will always stopped at depth-1 level function.
for example
function A() call function B()
function B() call function C()
function C() call function D()
fragment fail in function D() on purpose.
then the output backtrace will stop at function C()
In my view, it should stop at function D() at least.