Skip to content

Commit 1621455

Browse files
committed
Big refactoring to allow in the future to setup stacktrace depth
1 parent d7bd9eb commit 1621455

25 files changed

Lines changed: 830 additions & 1212 deletions

include/boost/detail/winapi/sym_from_addr.hpp

Lines changed: 0 additions & 64 deletions
This file was deleted.

include/boost/stacktrace.hpp

Lines changed: 38 additions & 95 deletions
Original file line numberDiff line numberDiff line change
@@ -21,64 +21,7 @@
2121
#include <iosfwd>
2222
#include <string>
2323

24-
/// @cond
25-
26-
// Link or header only
27-
#if !defined(BOOST_STACKTRACE_LINK) && defined(BOOST_STACKTRACE_DYN_LINK)
28-
# define BOOST_STACKTRACE_LINK
29-
#endif
30-
31-
#if defined(BOOST_STACKTRACE_LINK) && !defined(BOOST_STACKTRACE_DYN_LINK) && defined(BOOST_ALL_DYN_LINK)
32-
# define BOOST_STACKTRACE_DYN_LINK
33-
#endif
34-
35-
// Backend autodetection
36-
#if !defined(BOOST_STACKTRACE_USE_NOOP) && !defined(BOOST_STACKTRACE_USE_WINDBG) && !defined(BOOST_STACKTRACE_USE_LIBUNWIND) \
37-
&& !defined(BOOST_STACKTRACE_USE_BACKTRACE) &&!defined(BOOST_STACKTRACE_USE_HEADER)
38-
39-
#if defined(__has_include) && (!defined(__GNUC__) || __GNUC__ > 4 || BOOST_CLANG)
40-
# if __has_include(<libunwind.h>)
41-
# define BOOST_STACKTRACE_USE_LIBUNWIND
42-
# elif __has_include(<execinfo.h>)
43-
# define BOOST_STACKTRACE_USE_BACKTRACE
44-
# elif __has_include("DbgHelp.h")
45-
# define BOOST_STACKTRACE_USE_WINDBG
46-
# endif
47-
#else
48-
# if defined(BOOST_WINDOWS)
49-
# define BOOST_STACKTRACE_USE_WINDBG
50-
# else
51-
# define BOOST_STACKTRACE_USE_BACKTRACE
52-
# endif
53-
#endif
54-
55-
#endif
56-
57-
#ifdef BOOST_STACKTRACE_LINK
58-
# if defined(BOOST_STACKTRACE_DYN_LINK)
59-
# ifdef BOOST_STACKTRACE_INTERNAL_BUILD_LIBS
60-
# define BOOST_STACKTRACE_FUNCTION BOOST_SYMBOL_EXPORT
61-
# else
62-
# define BOOST_STACKTRACE_FUNCTION BOOST_SYMBOL_IMPORT
63-
# endif
64-
# else
65-
# define BOOST_STACKTRACE_FUNCTION
66-
# endif
67-
#else
68-
# define BOOST_STACKTRACE_FUNCTION inline
69-
# if defined(BOOST_STACKTRACE_USE_NOOP)
70-
# include <boost/stacktrace/detail/backtrace_holder_noop.hpp>
71-
# elif defined(BOOST_STACKTRACE_USE_WINDBG)
72-
# include <boost/stacktrace/detail/backtrace_holder_windows.hpp>
73-
# elif defined(BOOST_STACKTRACE_USE_LIBUNWIND)
74-
# include <boost/stacktrace/detail/backtrace_holder_libunwind.hpp>
75-
# elif defined(BOOST_STACKTRACE_USE_BACKTRACE)
76-
# include <boost/stacktrace/detail/backtrace_holder_linux.hpp>
77-
# else
78-
# error No suitable backtrace backend found
79-
# endif
80-
#endif
81-
/// @endcond
24+
#include <boost/stacktrace/detail/backend.hpp>
8225

8326
namespace boost { namespace stacktrace {
8427

@@ -90,12 +33,12 @@ namespace detail { class iterator; }
9033
/// Non-owning class that references the frame information stored inside the boost::stacktrace::stacktrace class.
9134
class frame_view {
9235
/// @cond
93-
const stacktrace* impl_;
36+
const boost::stacktrace::detail::backend* impl_;
9437
std::size_t frame_no_;
9538

9639
frame_view(); // = delete
9740

98-
frame_view(const stacktrace* impl, std::size_t frame_no) BOOST_NOEXCEPT
41+
frame_view(const boost::stacktrace::detail::backend* impl, std::size_t frame_no) BOOST_NOEXCEPT
9942
: impl_(impl)
10043
, frame_no_(frame_no)
10144
{}
@@ -156,7 +99,7 @@ namespace detail {
15699

157100
frame_view f_;
158101

159-
iterator(const stacktrace* impl, std::size_t frame_no) BOOST_NOEXCEPT
102+
iterator(const boost::stacktrace::detail::backend* impl, std::size_t frame_no) BOOST_NOEXCEPT
160103
: f_(impl, frame_no)
161104
{}
162105

@@ -195,21 +138,11 @@ namespace detail {
195138
/// Class that on construction copies minimal information about call stack into its internals and provides access to that information.
196139
class stacktrace {
197140
/// @cond
198-
#ifdef BOOST_STACKTRACE_LINK
199141
BOOST_STATIC_CONSTEXPR std::size_t max_implementation_size = sizeof(void*) * 110u;
200142
boost::aligned_storage<max_implementation_size>::type impl_;
201-
#else
202-
boost::stacktrace::detail::backtrace_holder impl_;
203-
#endif
204143
std::size_t hash_code_;
144+
boost::stacktrace::detail::backend back_;
205145

206-
BOOST_STACKTRACE_FUNCTION std::string get_name(std::size_t frame_no) const;
207-
BOOST_STACKTRACE_FUNCTION const void* get_address(std::size_t frame_no) const BOOST_NOEXCEPT;
208-
BOOST_STACKTRACE_FUNCTION std::string get_source_file(std::size_t frame_no) const;
209-
BOOST_STACKTRACE_FUNCTION std::size_t get_source_line(std::size_t frame_no) const BOOST_NOEXCEPT;
210-
/// @endcond
211-
212-
friend class frame_view;
213146
public:
214147
typedef frame_view reference;
215148

@@ -222,21 +155,35 @@ class stacktrace {
222155
/// @brief Stores the current function call sequence inside the class.
223156
///
224157
/// @b Complexity: O(N) where N is call seaquence length, O(1) for noop backend.
225-
BOOST_STACKTRACE_FUNCTION stacktrace() BOOST_NOEXCEPT;
158+
stacktrace() BOOST_NOEXCEPT
159+
: impl_()
160+
, hash_code_()
161+
, back_(&impl_, sizeof(impl_), hash_code_)
162+
{}
226163

227164
/// @b Complexity: O(1)
228-
BOOST_STACKTRACE_FUNCTION stacktrace(const stacktrace& bt) BOOST_NOEXCEPT;
165+
stacktrace(const stacktrace& st) BOOST_NOEXCEPT
166+
: impl_()
167+
, hash_code_(st.hash_code_)
168+
, back_(st.back_, &impl_)
169+
{}
229170

230171
/// @b Complexity: O(1)
231-
BOOST_STACKTRACE_FUNCTION stacktrace& operator=(const stacktrace& bt) BOOST_NOEXCEPT;
172+
stacktrace& operator=(const stacktrace& st) BOOST_NOEXCEPT {
173+
back_.~backend();
174+
new (&back_) boost::stacktrace::detail::backend(st.back_, &impl_);
175+
return *this;
176+
}
232177

233178
/// @b Complexity: O(N) for libunwind, O(1) for other backends.
234-
BOOST_STACKTRACE_FUNCTION ~stacktrace() BOOST_NOEXCEPT;
179+
~stacktrace() BOOST_NOEXCEPT {}
235180

236181
/// @returns Number of function names stored inside the class.
237182
///
238183
/// @b Complexity: O(1)
239-
BOOST_STACKTRACE_FUNCTION std::size_t size() const BOOST_NOEXCEPT;
184+
std::size_t size() const BOOST_NOEXCEPT {
185+
return back_.size();
186+
}
240187

241188
/// @param frame_no Zero based index of frame to return. 0
242189
/// is the function index where stacktrace was constructed and
@@ -250,22 +197,22 @@ class stacktrace {
250197

251198

252199
/// @b Complexity: O(1)
253-
const_iterator begin() const BOOST_NOEXCEPT { return const_iterator(this, 0); }
200+
const_iterator begin() const BOOST_NOEXCEPT { return const_iterator(&back_, 0); }
254201
/// @b Complexity: O(1)
255-
const_iterator cbegin() const BOOST_NOEXCEPT { return const_iterator(this, 0); }
202+
const_iterator cbegin() const BOOST_NOEXCEPT { return const_iterator(&back_, 0); }
256203
/// @b Complexity: O(1)
257-
const_iterator end() const BOOST_NOEXCEPT { return const_iterator(this, size()); }
204+
const_iterator end() const BOOST_NOEXCEPT { return const_iterator(&back_, size()); }
258205
/// @b Complexity: O(1)
259-
const_iterator cend() const BOOST_NOEXCEPT { return const_iterator(this, size()); }
206+
const_iterator cend() const BOOST_NOEXCEPT { return const_iterator(&back_, size()); }
260207

261208
/// @b Complexity: O(1)
262-
const_reverse_iterator rbegin() const BOOST_NOEXCEPT { return const_reverse_iterator( const_iterator(this, 0) ); }
209+
const_reverse_iterator rbegin() const BOOST_NOEXCEPT { return const_reverse_iterator( const_iterator(&back_, 0) ); }
263210
/// @b Complexity: O(1)
264-
const_reverse_iterator crbegin() const BOOST_NOEXCEPT { return const_reverse_iterator( const_iterator(this, 0) ); }
211+
const_reverse_iterator crbegin() const BOOST_NOEXCEPT { return const_reverse_iterator( const_iterator(&back_, 0) ); }
265212
/// @b Complexity: O(1)
266-
const_reverse_iterator rend() const BOOST_NOEXCEPT { return const_reverse_iterator( const_iterator(this, size()) ); }
213+
const_reverse_iterator rend() const BOOST_NOEXCEPT { return const_reverse_iterator( const_iterator(&back_, size()) ); }
267214
/// @b Complexity: O(1)
268-
const_reverse_iterator crend() const BOOST_NOEXCEPT { return const_reverse_iterator( const_iterator(this, size()) ); }
215+
const_reverse_iterator crend() const BOOST_NOEXCEPT { return const_reverse_iterator( const_iterator(&back_, size()) ); }
269216

270217

271218
/// @brief Allows to check that stack trace capturing was successful.
@@ -277,12 +224,16 @@ class stacktrace {
277224
/// @brief Compares stacktraces for less, order is platform dependant.
278225
///
279226
/// @b Complexity: Amortized O(1); worst case O(size())
280-
BOOST_STACKTRACE_FUNCTION bool operator< (const stacktrace& rhs) const BOOST_NOEXCEPT;
227+
bool operator< (const stacktrace& rhs) const BOOST_NOEXCEPT {
228+
return hash_code_ < rhs.hash_code_ || (hash_code_ == rhs.hash_code_ && back_ < rhs.back_);
229+
}
281230

282231
/// @brief Compares stacktraces for equality.
283232
///
284233
/// @b Complexity: Amortized O(1); worst case O(size())
285-
BOOST_STACKTRACE_FUNCTION bool operator==(const stacktrace& rhs) const BOOST_NOEXCEPT;
234+
bool operator==(const stacktrace& rhs) const BOOST_NOEXCEPT {
235+
return hash_code_ == rhs.hash_code_ && back_ == rhs.back_;
236+
}
286237

287238
/// @brief Returns hashed code of the stacktrace.
288239
///
@@ -371,12 +322,4 @@ std::basic_ostream<CharT, TraitsT>& operator<<(std::basic_ostream<CharT, TraitsT
371322

372323
}} // namespace boost::stacktrace
373324

374-
/// @cond
375-
#undef BOOST_STACKTRACE_FUNCTION
376-
377-
#ifndef BOOST_STACKTRACE_LINK
378-
# include <boost/stacktrace/detail/stacktrace.ipp>
379-
#endif
380-
/// @endcond
381-
382325
#endif // BOOST_STACKTRACE_STACKTRACE_HPP
Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,103 @@
1+
// Copyright Antony Polukhin, 2016.
2+
//
3+
// Distributed under the Boost Software License, Version 1.0. (See
4+
// accompanying file LICENSE_1_0.txt or copy at
5+
// http://www.boost.org/LICENSE_1_0.txt)
6+
7+
#ifndef BOOST_STACKTRACE_DETAIL_BACKEND_HPP
8+
#define BOOST_STACKTRACE_DETAIL_BACKEND_HPP
9+
10+
#include <boost/config.hpp>
11+
#ifdef BOOST_HAS_PRAGMA_ONCE
12+
# pragma once
13+
#endif
14+
15+
#include <boost/core/noncopyable.hpp>
16+
#include <string>
17+
18+
// Link or header only
19+
#if !defined(BOOST_STACKTRACE_LINK) && defined(BOOST_STACKTRACE_DYN_LINK)
20+
# define BOOST_STACKTRACE_LINK
21+
#endif
22+
23+
#if defined(BOOST_STACKTRACE_LINK) && !defined(BOOST_STACKTRACE_DYN_LINK) && defined(BOOST_ALL_DYN_LINK)
24+
# define BOOST_STACKTRACE_DYN_LINK
25+
#endif
26+
27+
// Backend autodetection
28+
#if !defined(BOOST_STACKTRACE_USE_NOOP) && !defined(BOOST_STACKTRACE_USE_WINDBG) && !defined(BOOST_STACKTRACE_USE_LIBUNWIND) \
29+
&& !defined(BOOST_STACKTRACE_USE_BACKTRACE) &&!defined(BOOST_STACKTRACE_USE_HEADER)
30+
31+
#if defined(__has_include) && (!defined(__GNUC__) || __GNUC__ > 4 || BOOST_CLANG)
32+
# if __has_include(<libunwind.h>)
33+
# define BOOST_STACKTRACE_USE_LIBUNWIND
34+
# elif __has_include(<execinfo.h>)
35+
# define BOOST_STACKTRACE_USE_BACKTRACE
36+
# elif __has_include("Dbgeng.h")
37+
# define BOOST_STACKTRACE_USE_WINDBG
38+
# endif
39+
#else
40+
# if defined(BOOST_WINDOWS)
41+
# define BOOST_STACKTRACE_USE_WINDBG
42+
# else
43+
# define BOOST_STACKTRACE_USE_BACKTRACE
44+
# endif
45+
#endif
46+
47+
#endif
48+
49+
#ifdef BOOST_STACKTRACE_LINK
50+
# if defined(BOOST_STACKTRACE_DYN_LINK)
51+
# ifdef BOOST_STACKTRACE_INTERNAL_BUILD_LIBS
52+
# define BOOST_STACKTRACE_FUNCTION BOOST_SYMBOL_EXPORT
53+
# else
54+
# define BOOST_STACKTRACE_FUNCTION BOOST_SYMBOL_IMPORT
55+
# endif
56+
# else
57+
# define BOOST_STACKTRACE_FUNCTION
58+
# endif
59+
#else
60+
# define BOOST_STACKTRACE_FUNCTION BOOST_FORCEINLINE
61+
#endif
62+
63+
namespace boost { namespace stacktrace { namespace detail {
64+
65+
struct backtrace_holder;
66+
67+
// Class that implements the actual backtracing
68+
class backend: boost::noncopyable {
69+
void* data_;
70+
71+
inline boost::stacktrace::detail::backtrace_holder& impl() BOOST_NOEXCEPT {
72+
return *reinterpret_cast<boost::stacktrace::detail::backtrace_holder*>(data_);
73+
}
74+
75+
inline const boost::stacktrace::detail::backtrace_holder& impl() const BOOST_NOEXCEPT {
76+
return *reinterpret_cast<const boost::stacktrace::detail::backtrace_holder*>(data_);
77+
}
78+
79+
public:
80+
BOOST_STACKTRACE_FUNCTION backend(void* memory, std::size_t size, std::size_t& hash_code) BOOST_NOEXCEPT;
81+
BOOST_STACKTRACE_FUNCTION std::string get_name(std::size_t frame_no) const;
82+
BOOST_STACKTRACE_FUNCTION const void* get_address(std::size_t frame_no) const BOOST_NOEXCEPT;
83+
BOOST_STACKTRACE_FUNCTION std::string get_source_file(std::size_t frame_no) const;
84+
BOOST_STACKTRACE_FUNCTION std::size_t get_source_line(std::size_t frame_no) const BOOST_NOEXCEPT;
85+
BOOST_STACKTRACE_FUNCTION bool operator< (const backend& rhs) const BOOST_NOEXCEPT;
86+
BOOST_STACKTRACE_FUNCTION bool operator==(const backend& rhs) const BOOST_NOEXCEPT;
87+
88+
BOOST_STACKTRACE_FUNCTION backend(const backend& b, void* memory) BOOST_NOEXCEPT;
89+
BOOST_STACKTRACE_FUNCTION ~backend() BOOST_NOEXCEPT;
90+
BOOST_STACKTRACE_FUNCTION std::size_t size() const BOOST_NOEXCEPT;
91+
};
92+
93+
}}} // namespace boost::stacktrace::detail
94+
95+
/// @cond
96+
#undef BOOST_STACKTRACE_FUNCTION
97+
98+
#ifndef BOOST_STACKTRACE_LINK
99+
# include <boost/stacktrace/detail/backend.ipp>
100+
#endif
101+
/// @endcond
102+
103+
#endif // BOOST_STACKTRACE_DETAIL_BACKEND_HPP

0 commit comments

Comments
 (0)