<div dir="ltr">Hi,<div><br></div><div>The gcc builtin functions (and libunwind) and only work if the stack frame information is not optimised away, this is controlled by gcc compiler flags, see; <a href="https://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html">https://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html</a> <span style="color:rgb(0,0,0);font-family:monospace;font-size:medium">-fomit-frame-pointer</span></div><div><span style="color:rgb(0,0,0);font-family:monospace;font-size:medium"><br></span></div><div><span style="color:rgb(0,0,0);font-family:monospace;font-size:medium">Without that you have to do your own unwinding, for example on x86 you could do the following, but its pretty crude. Linux/FreeBSD do much more fancy unwinders, it depends on what you want.</span></div><div><span style="color:rgb(0,0,0);font-family:monospace;font-size:medium"><br></span></div><div><div><font color="#000000" face="monospace" size="3">#define get_ebp()       \</font></div><div><font color="#000000" face="monospace" size="3">({ unsigned long  __value;   \</font></div><div><font color="#000000" face="monospace" size="3">   asm volatile (" mov %%ebp,%0": "=a"(__value));  \</font></div><div><font color="#000000" face="monospace" size="3">   __value; })</font></div></div><div><font color="#000000" face="monospace" size="3"><br></font></div><div><font color="#000000" face="monospace" size="3"><div>void error_dump_callstack(int fd)</div><div>{</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">    </span>unsigned long<span class="gmail-Apple-tab-span" style="white-space:pre"> </span>ebp=0,arg0,arg4,arg8,arg12,arg16;</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">      </span>int i;</div><div><br></div><div><span class="gmail-Apple-tab-span" style="white-space:pre">        </span>arg0 = get_ebp(); // base pointer, start of current stack frame</div><div><br></div><div><span class="gmail-Apple-tab-span" style="white-space:pre">       </span>assert_out(fd,"\r\nCall Stack Information:\r\n\r\n");</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">        </span>for (i=0; i<15; i++)</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">        </span>{</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">              </span>// attempt get backtrace (with arguments) from stored EPB</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">              </span>arg0 = *(unsigned long*)(arg0);</div><div><br></div><div><span class="gmail-Apple-tab-span" style="white-space:pre">               </span>if (arg0 == 0)</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">                 </span>break;</div><div><br></div><div><span class="gmail-Apple-tab-span" style="white-space:pre">                </span>// print stackframe back past inturrupt</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">                </span>arg0 = *(unsigned long*)(arg0);</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">                </span>arg4 = *(unsigned long*)(arg0+4);</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">              </span>arg8 = *(unsigned long*)(arg0+8);</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">              </span>arg12 = *(unsigned long*)(arg0+12);</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">            </span>arg16 = *(unsigned long*)(arg0+16);</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">            </span></div><div><span class="gmail-Apple-tab-span" style="white-space:pre">               </span>sprintf(assertbuffer,"ebp:     %p\r\nframe%d:  %p\r\narg1:    %p\r\narg2:    %p\r\narg3:    %p\r\n",arg0,i,arg4,arg8,arg12,arg16);</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">          </span>assert_out(fd,assertbuffer);</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">   </span>}</div><div><span class="gmail-Apple-tab-span" style="white-space:pre">      </span></div><div><span class="gmail-Apple-tab-span" style="white-space:pre">       </span>assert_out(fd,"use 'addr2line -C -e abc.elf -f address' to get symbol names\r\n");</div><div>}</div><div><br></div><div><br></div></font></div><div><span style="color:rgb(0,0,0);font-family:monospace;font-size:medium"><br></span></div><div><span style="color:rgb(0,0,0);font-family:monospace;font-size:medium"><br></span></div></div><div class="gmail_extra"><br><div class="gmail_quote">On 6 December 2016 at 22:36, Chris Johns <span dir="ltr"><<a href="mailto:chrisj@rtems.org" target="_blank">chrisj@rtems.org</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">On 06/12/2016 01:46, Jan Sommer wrote:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
Is there a common way how to create stacktraces in RTEMS?<br>
</blockquote>
<br>
Not that I know of.<br>
<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
I tried to use the _Unwind_Backtrace_-function from gcc, but so far it<br>
only returns _URC_END_OF_STACK if I call it from a leaf function<br>
(haven't tried a trap handler yet).<br>
</blockquote>
<br>
The end of stack code means the unwinder could not find any data about the frames in the stack. The default DWARF unwinder, which SPARC uses, searches for a valid Frame Description Entry (FDE) and if not found reports the end of stack code. If an FDE is found the Common Information Entry (CIE) is extracted from that data and the frame info decoded.<br>
<br>
C++ uses the same process for exceptions. A .eh_frame plus some other sections are created and the frames effected by the exceptions added to these sections. These sections are registered at start up. For a DWARF unwinder, which includes the SPARC, the DWARF standard is used for the format of these sections.<br>
<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
I am not sure if that is the way to go.<br>
</blockquote>
<br>
I am not 100% sure myself. I think you would need to include some level of DWARF related information in the executable to do this. This information would need to be registered with the DWARF unwinder code via something like 'void __register_frame (void *begin)'.<br>
<br>
I would also take a look at FreeBSD and see how they implement the unwinder. I do not know if the FreeBSD kernel has one.<br>
<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
Are there any recommendations or examples for this topic?<br>
</blockquote>
<br>
The DWARF standard website is the best source of info:<br>
<br>
<a href="http://dwarfstd.org/" rel="noreferrer" target="_blank">http://dwarfstd.org/</a><br>
<br>
Chris<br>
<br>
______________________________<wbr>_________________<br>
users mailing list<br>
<a href="mailto:users@rtems.org" target="_blank">users@rtems.org</a><br>
<a href="http://lists.rtems.org/mailman/listinfo/users" rel="noreferrer" target="_blank">http://lists.rtems.org/mailman<wbr>/listinfo/users</a><br>
</blockquote></div><br><br clear="all"><div><br></div>-- <br><div class="gmail_signature" data-smartmail="gmail_signature"><div><br>regards</div><div>---</div><div>Matthew J Fletcher</div><br></div>
</div>