Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(244)

Side by Side Diff: base/debug/stack_trace_posix.cc

Issue 1879073002: Add function to trace stack using frame pointers. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Address comments Created 4 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "base/debug/stack_trace.h" 5 #include "base/debug/stack_trace.h"
6 6
7 #include <errno.h> 7 #include <errno.h>
8 #include <fcntl.h> 8 #include <fcntl.h>
9 #include <signal.h> 9 #include <signal.h>
10 #include <stddef.h> 10 #include <stddef.h>
(...skipping 725 matching lines...) Expand 10 before | Expand all | Expand 10 after
736 #endif 736 #endif
737 } 737 }
738 738
739 #if !defined(__UCLIBC__) 739 #if !defined(__UCLIBC__)
740 void StackTrace::OutputToStream(std::ostream* os) const { 740 void StackTrace::OutputToStream(std::ostream* os) const {
741 StreamBacktraceOutputHandler handler(os); 741 StreamBacktraceOutputHandler handler(os);
742 ProcessBacktrace(trace_, count_, &handler); 742 ProcessBacktrace(trace_, count_, &handler);
743 } 743 }
744 #endif 744 #endif
745 745
746 #if HAVE_TRACE_STACK_FRAME_POINTERS
747
748 size_t TraceStackFramePointers(const void** out_trace,
749 size_t max_depth,
750 size_t skip_initial) {
751 uintptr_t fp = reinterpret_cast<uintptr_t>(__builtin_frame_address(0));
Nico 2016/04/18 19:42:05 nit: call this sp
Dmitry Skiba 2016/04/20 16:32:56 Done.
752
753 size_t depth = 0;
754 while (fp && depth < max_depth) {
755 if (skip_initial != 0) {
756 skip_initial--;
757 } else {
758 out_trace[depth++] = reinterpret_cast<const void**>(fp)[1];
Nico 2016/04/18 19:42:05 you treat fp as void** almost everywhere, consider
Primiano Tucci (use gerrit) 2016/04/18 20:18:07 the frame pointer can be invalid even at this stag
Dmitry Skiba 2016/04/20 16:32:56 Hmm, since I don't have next_fp at that point, I c
Dmitry Skiba 2016/04/20 16:32:56 So we have these casts: reinterpret_cast<uintptr_
759 }
760
761 // Find out next frame pointer
762 // (heuristics are from TCMalloc's stacktrace functions)
763 {
Primiano Tucci (use gerrit) 2016/04/18 20:18:08 why this is inside a scope? Is there an if missing
Dmitry Skiba 2016/04/20 16:32:56 Done.
764 uintptr_t next_fp = reinterpret_cast<const uintptr_t*>(fp)[0];
765
766 // With the stack growing downwards, older stack frame must be
767 // at a greater address that the current one.
768 if (next_fp <= fp) break;
Primiano Tucci (use gerrit) 2016/04/18 20:18:08 I think these checks should happen before you dere
Dmitry Skiba 2016/04/20 16:32:56 But this also dereferences fp, next_fp is fp[1].
769
770 // Assume stack frames larger than 100,000 bytes are bogus.
771 if (next_fp - fp > 100000) break;
772
773 // Check alignment.
774 if (next_fp & (sizeof(void*) - 1)) break;
775
776 fp = next_fp;
777 }
778 }
779
780 return depth;
781 }
782
783 #endif // HAVE_TRACE_STACK_FRAME_POINTERS
784
746 namespace internal { 785 namespace internal {
747 786
748 // NOTE: code from sandbox/linux/seccomp-bpf/demo.cc. 787 // NOTE: code from sandbox/linux/seccomp-bpf/demo.cc.
749 char* itoa_r(intptr_t i, char* buf, size_t sz, int base, size_t padding) { 788 char* itoa_r(intptr_t i, char* buf, size_t sz, int base, size_t padding) {
750 // Make sure we can write at least one NUL byte. 789 // Make sure we can write at least one NUL byte.
751 size_t n = 1; 790 size_t n = 1;
752 if (n > sz) 791 if (n > sz)
753 return NULL; 792 return NULL;
754 793
755 if (base < 2 || base > 16) { 794 if (base < 2 || base > 16) {
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
804 *ptr = *start; 843 *ptr = *start;
805 *start++ = ch; 844 *start++ = ch;
806 } 845 }
807 return buf; 846 return buf;
808 } 847 }
809 848
810 } // namespace internal 849 } // namespace internal
811 850
812 } // namespace debug 851 } // namespace debug
813 } // namespace base 852 } // namespace base
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698