OLD | NEW |
1 // Copyright (c) 2005, Google Inc. | 1 // Copyright (c) 2005, Google Inc. |
2 // All rights reserved. | 2 // All rights reserved. |
3 // | 3 // |
4 // Redistribution and use in source and binary forms, with or without | 4 // Redistribution and use in source and binary forms, with or without |
5 // modification, are permitted provided that the following conditions are | 5 // modification, are permitted provided that the following conditions are |
6 // met: | 6 // met: |
7 // | 7 // |
8 // * Redistributions of source code must retain the above copyright | 8 // * Redistributions of source code must retain the above copyright |
9 // notice, this list of conditions and the following disclaimer. | 9 // notice, this list of conditions and the following disclaimer. |
10 // * Redistributions in binary form must reproduce the above | 10 // * Redistributions in binary form must reproduce the above |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
58 #endif | 58 #endif |
59 #ifdef HAVE_UNISTD_H | 59 #ifdef HAVE_UNISTD_H |
60 #include <unistd.h> | 60 #include <unistd.h> |
61 #endif | 61 #endif |
62 #ifdef HAVE_MMAP | 62 #ifdef HAVE_MMAP |
63 #include <sys/mman.h> // for msync | 63 #include <sys/mman.h> // for msync |
64 #include "base/vdso_support.h" | 64 #include "base/vdso_support.h" |
65 #endif | 65 #endif |
66 | 66 |
67 #include "google/stacktrace.h" | 67 #include "google/stacktrace.h" |
| 68 #if defined(KEEP_SHADOW_STACKS) |
| 69 #include "linux_shadow_stacks.h" |
| 70 #endif // KEEP_SHADOW_STACKS |
68 | 71 |
69 #if defined(__linux__) && defined(__i386__) && defined(__ELF__) && defined(HAVE_
MMAP) | 72 #if defined(__linux__) && defined(__i386__) && defined(__ELF__) && defined(HAVE_
MMAP) |
70 // Count "push %reg" instructions in VDSO __kernel_vsyscall(), | 73 // Count "push %reg" instructions in VDSO __kernel_vsyscall(), |
71 // preceeding "syscall" or "sysenter". | 74 // preceeding "syscall" or "sysenter". |
72 // If __kernel_vsyscall uses frame pointer, answer 0. | 75 // If __kernel_vsyscall uses frame pointer, answer 0. |
73 // | 76 // |
74 // kMaxBytes tells how many instruction bytes of __kernel_vsyscall | 77 // kMaxBytes tells how many instruction bytes of __kernel_vsyscall |
75 // to analyze before giving up. Up to kMaxBytes+1 bytes of | 78 // to analyze before giving up. Up to kMaxBytes+1 bytes of |
76 // instructions could be accessed. | 79 // instructions could be accessed. |
77 // | 80 // |
(...skipping 236 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
314 // static void Noop() { asm(""); } // prevent optimizing-away | 317 // static void Noop() { asm(""); } // prevent optimizing-away |
315 __asm__ volatile ("mov %%rbp, %0" : "=r" (rbp)); | 318 __asm__ volatile ("mov %%rbp, %0" : "=r" (rbp)); |
316 // Arguments are passed in registers on x86-64, so we can't just | 319 // Arguments are passed in registers on x86-64, so we can't just |
317 // offset from &result | 320 // offset from &result |
318 sp = (void **) rbp; | 321 sp = (void **) rbp; |
319 #else | 322 #else |
320 # error Using stacktrace_x86-inl.h on a non x86 architecture! | 323 # error Using stacktrace_x86-inl.h on a non x86 architecture! |
321 #endif | 324 #endif |
322 | 325 |
323 int n = 0; | 326 int n = 0; |
| 327 #if defined(KEEP_SHADOW_STACKS) |
| 328 void **shadow_ip_stack; |
| 329 void **shadow_sp_stack; |
| 330 int stack_size; |
| 331 shadow_ip_stack = (void**) get_shadow_ip_stack(&stack_size); |
| 332 shadow_sp_stack = (void**) get_shadow_sp_stack(&stack_size); |
| 333 int shadow_index = stack_size - 1; |
| 334 for (int i = stack_size - 1; i >= 0; i--) { |
| 335 if (sp == shadow_sp_stack[i]) { |
| 336 shadow_index = i; |
| 337 break; |
| 338 } |
| 339 } |
| 340 void **prev_sp = NULL; |
| 341 #endif // KEEP_SHADOW_STACKS |
324 while (sp && n < max_depth) { | 342 while (sp && n < max_depth) { |
325 if (*(sp+1) == reinterpret_cast<void *>(0)) { | 343 if (*(sp+1) == reinterpret_cast<void *>(0)) { |
326 // In 64-bit code, we often see a frame that | 344 // In 64-bit code, we often see a frame that |
327 // points to itself and has a return address of 0. | 345 // points to itself and has a return address of 0. |
328 break; | 346 break; |
329 } | 347 } |
330 #if !IS_WITH_CONTEXT | 348 #if !IS_WITH_CONTEXT |
331 const void *const ucp = NULL; | 349 const void *const ucp = NULL; |
332 #endif | 350 #endif |
333 void **next_sp = NextStackFrame<!IS_STACK_FRAMES, IS_WITH_CONTEXT>(sp, ucp); | 351 void **next_sp = NextStackFrame<!IS_STACK_FRAMES, IS_WITH_CONTEXT>(sp, ucp); |
334 if (skip_count > 0) { | 352 if (skip_count > 0) { |
335 skip_count--; | 353 skip_count--; |
| 354 #if defined(KEEP_SHADOW_STACKS) |
| 355 shadow_index--; |
| 356 #endif // KEEP_SHADOW_STACKS |
336 } else { | 357 } else { |
337 result[n] = *(sp+1); | 358 result[n] = *(sp+1); |
| 359 #if defined(KEEP_SHADOW_STACKS) |
| 360 if ((shadow_index > 0) && (sp == shadow_sp_stack[shadow_index])) { |
| 361 shadow_index--; |
| 362 } |
| 363 #endif // KEEP_SHADOW_STACKS |
| 364 |
338 #if IS_STACK_FRAMES | 365 #if IS_STACK_FRAMES |
339 if (next_sp > sp) { | 366 if (next_sp > sp) { |
340 sizes[n] = (uintptr_t)next_sp - (uintptr_t)sp; | 367 sizes[n] = (uintptr_t)next_sp - (uintptr_t)sp; |
341 } else { | 368 } else { |
342 // A frame-size of 0 is used to indicate unknown frame size. | 369 // A frame-size of 0 is used to indicate unknown frame size. |
343 sizes[n] = 0; | 370 sizes[n] = 0; |
344 } | 371 } |
345 #endif | 372 #endif |
346 n++; | 373 n++; |
347 } | 374 } |
| 375 #if defined(KEEP_SHADOW_STACKS) |
| 376 prev_sp = sp; |
| 377 #endif // KEEP_SHADOW_STACKS |
348 sp = next_sp; | 378 sp = next_sp; |
349 } | 379 } |
| 380 |
| 381 #if defined(KEEP_SHADOW_STACKS) |
| 382 if (shadow_index >= 0) { |
| 383 for (int i = shadow_index; i >= 0; i--) { |
| 384 if (shadow_sp_stack[i] > prev_sp) { |
| 385 result[n] = shadow_ip_stack[i]; |
| 386 if (n + 1 < max_depth) { |
| 387 n++; |
| 388 continue; |
| 389 } |
| 390 } |
| 391 break; |
| 392 } |
| 393 } |
| 394 #endif // KEEP_SHADOW_STACKS |
350 return n; | 395 return n; |
351 } | 396 } |
OLD | NEW |