+int silc_st_backtrace(void **stack)
+{
+#if defined(HAVE_BACKTRACE)
+ return backtrace(stack, SILC_ST_DEPTH);
+#else
+ void *fp;
+ int depth;
+ asm volatile ("movl %%ebp, %0" : "=r" (fp));
+ for (depth = 0; fp; depth++) {
+ if (depth == SILC_ST_DEPTH)
+ break;
+
+ /* Get program pointer and frame pointer from this frame */
+ stack[depth] = *((void **)(((unsigned char *)fp) + 4));
+ fp = *((void **)fp);
+ }
+ return depth;
+#endif /* HAVE_BACKTRACE */
+}
+
+char **silc_st_backtrace_symbols(void **stack, int depth)
+{
+#if defined(HAVE_BACKTRACE)
+ return backtrace_symbols(stack, depth);
+#else
+ return NULL;
+#endif /* HAVE_BACKTRACE */
+}
+
+void silc_st_backtrace_symbols_stderr(void **stack, int depth)
+{
+#if defined(HAVE_BACKTRACE)
+ backtrace_symbols_fd(stack, depth, 2);
+#else
+ int i;
+ for (i = 0; i < depth; i++)
+ fprintf(stderr, "? [%p]\n", stack[i]);
+#endif /* HAVE_BACKTRACE */
+}
+