| Index: third_party/tcmalloc/chromium/src/stacktrace_x86-inl.h
|
| ===================================================================
|
| --- third_party/tcmalloc/chromium/src/stacktrace_x86-inl.h (revision 57513)
|
| +++ third_party/tcmalloc/chromium/src/stacktrace_x86-inl.h (working copy)
|
| @@ -65,6 +65,9 @@
|
| #endif
|
|
|
| #include "google/stacktrace.h"
|
| +#if defined(KEEP_SHADOW_STACKS)
|
| +#include "linux_shadow_stacks.h"
|
| +#endif // KEEP_SHADOW_STACKS
|
|
|
| #if defined(__linux__) && defined(__i386__) && defined(__ELF__) && defined(HAVE_MMAP)
|
| // Count "push %reg" instructions in VDSO __kernel_vsyscall(),
|
| @@ -316,6 +319,21 @@
|
| #endif
|
|
|
| int n = 0;
|
| +#if defined(KEEP_SHADOW_STACKS)
|
| + void **shadow_ip_stack;
|
| + void **shadow_sp_stack;
|
| + int stack_size;
|
| + shadow_ip_stack = (void**) get_shadow_ip_stack(&stack_size);
|
| + shadow_sp_stack = (void**) get_shadow_sp_stack(&stack_size);
|
| + int shadow_index = stack_size - 1;
|
| + for (int i = stack_size - 1; i >= 0; i--) {
|
| + if (sp == shadow_sp_stack[i]) {
|
| + shadow_index = i;
|
| + break;
|
| + }
|
| + }
|
| + void **prev_sp = NULL;
|
| +#endif // KEEP_SHADOW_STACKS
|
| while (sp && n < max_depth) {
|
| if (*(sp+1) == reinterpret_cast<void *>(0)) {
|
| // In 64-bit code, we often see a frame that
|
| @@ -328,8 +346,17 @@
|
| void **next_sp = NextStackFrame<!IS_STACK_FRAMES, IS_WITH_CONTEXT>(sp, ucp);
|
| if (skip_count > 0) {
|
| skip_count--;
|
| +#if defined(KEEP_SHADOW_STACKS)
|
| + shadow_index--;
|
| +#endif // KEEP_SHADOW_STACKS
|
| } else {
|
| result[n] = *(sp+1);
|
| +#if defined(KEEP_SHADOW_STACKS)
|
| + if ((shadow_index > 0) && (sp == shadow_sp_stack[shadow_index])) {
|
| + shadow_index--;
|
| + }
|
| +#endif // KEEP_SHADOW_STACKS
|
| +
|
| #if IS_STACK_FRAMES
|
| if (next_sp > sp) {
|
| sizes[n] = (uintptr_t)next_sp - (uintptr_t)sp;
|
| @@ -340,7 +367,25 @@
|
| #endif
|
| n++;
|
| }
|
| +#if defined(KEEP_SHADOW_STACKS)
|
| + prev_sp = sp;
|
| +#endif // KEEP_SHADOW_STACKS
|
| sp = next_sp;
|
| }
|
| +
|
| +#if defined(KEEP_SHADOW_STACKS)
|
| + if (shadow_index >= 0) {
|
| + for (int i = shadow_index; i >= 0; i--) {
|
| + if (shadow_sp_stack[i] > prev_sp) {
|
| + result[n] = shadow_ip_stack[i];
|
| + if (n + 1 < max_depth) {
|
| + n++;
|
| + continue;
|
| + }
|
| + }
|
| + break;
|
| + }
|
| + }
|
| +#endif // KEEP_SHADOW_STACKS
|
| return n;
|
| }
|
|
|