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

Side by Side Diff: base/profiler/stack_sampling_profiler.h

Issue 2444143002: Add process lifetime annotations to stack samples. (Closed)
Patch Set: addressed review comments by wittman Created 4 years, 1 month 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 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2015 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 #ifndef BASE_PROFILER_STACK_SAMPLING_PROFILER_H_ 5 #ifndef BASE_PROFILER_STACK_SAMPLING_PROFILER_H_
6 #define BASE_PROFILER_STACK_SAMPLING_PROFILER_H_ 6 #define BASE_PROFILER_STACK_SAMPLING_PROFILER_H_
7 7
8 #include <stddef.h> 8 #include <stddef.h>
9 9
10 #include <memory> 10 #include <memory>
11 #include <string> 11 #include <string>
12 #include <vector> 12 #include <vector>
13 13
14 #include "base/atomicops.h"
14 #include "base/base_export.h" 15 #include "base/base_export.h"
15 #include "base/callback.h" 16 #include "base/callback.h"
16 #include "base/files/file_path.h" 17 #include "base/files/file_path.h"
17 #include "base/macros.h" 18 #include "base/macros.h"
18 #include "base/strings/string16.h" 19 #include "base/strings/string16.h"
19 #include "base/synchronization/waitable_event.h" 20 #include "base/synchronization/waitable_event.h"
20 #include "base/threading/platform_thread.h" 21 #include "base/threading/platform_thread.h"
21 #include "base/time/time.h" 22 #include "base/time/time.h"
22 23
23 namespace base { 24 namespace base {
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
57 // completed callback is called from a thread created by the profiler with the 58 // completed callback is called from a thread created by the profiler with the
58 // collected profiles. 59 // collected profiles.
59 // 60 //
60 // The results of the profiling are passed to the completed callback and consist 61 // The results of the profiling are passed to the completed callback and consist
61 // of a vector of CallStackProfiles. Each CallStackProfile corresponds to a 62 // of a vector of CallStackProfiles. Each CallStackProfile corresponds to a
62 // burst as specified in SamplingParams and contains a set of Samples and 63 // burst as specified in SamplingParams and contains a set of Samples and
63 // Modules. One Sample corresponds to a single recorded stack, and the Modules 64 // Modules. One Sample corresponds to a single recorded stack, and the Modules
64 // record those modules associated with the recorded stack frames. 65 // record those modules associated with the recorded stack frames.
65 class BASE_EXPORT StackSamplingProfiler { 66 class BASE_EXPORT StackSamplingProfiler {
66 public: 67 public:
68 enum ProcessPhase {
69 // TODO: Expand this.
70 FirstNonEmptyPaint,
71 };
72
73 enum ProcessActivity {
74 // TODO: Expand this, too.
75 };
76
67 // Module represents the module (DLL or exe) corresponding to a stack frame. 77 // Module represents the module (DLL or exe) corresponding to a stack frame.
68 struct BASE_EXPORT Module { 78 struct BASE_EXPORT Module {
69 Module(); 79 Module();
70 Module(uintptr_t base_address, 80 Module(uintptr_t base_address,
71 const std::string& id, 81 const std::string& id,
72 const FilePath& filename); 82 const FilePath& filename);
73 ~Module(); 83 ~Module();
74 84
75 // Points to the base address of the module. 85 // Points to the base address of the module.
76 uintptr_t base_address; 86 uintptr_t base_address;
(...skipping 23 matching lines...) Expand all
100 Frame(); 110 Frame();
101 111
102 // The sampled instruction pointer within the function. 112 // The sampled instruction pointer within the function.
103 uintptr_t instruction_pointer; 113 uintptr_t instruction_pointer;
104 114
105 // Index of the module in CallStackProfile::modules. We don't represent 115 // Index of the module in CallStackProfile::modules. We don't represent
106 // module state directly here to save space. 116 // module state directly here to save space.
107 size_t module_index; 117 size_t module_index;
108 }; 118 };
109 119
110 // Sample represents a set of stack frames. 120 // Sample represents a set of stack frames with some extra information.
111 using Sample = std::vector<Frame>; 121 struct BASE_EXPORT Sample {
122 Sample();
123 Sample(const Sample& sample);
124 ~Sample();
125
126 // These constructors are used only during testing.
127 Sample(const Frame& frame);
128 Sample(const std::vector<Frame>& frames);
129
130 // The entire stack frame when the sample is taken.
131 std::vector<Frame> frames;
132
133 // A bit-field indicating which process phases have passed. This can be
134 // used to tell where in the process lifetime the samples are taken. See
135 // ProcessPhase, above.
136 uint32_t process_phases = 0;
137
138 // A bit-field indicating activities which were active when the frame was
139 // captured. See ProcessActivity, above.
140 uint32_t current_activities = 0;
141 };
112 142
113 // CallStackProfile represents a set of samples. 143 // CallStackProfile represents a set of samples.
114 struct BASE_EXPORT CallStackProfile { 144 struct BASE_EXPORT CallStackProfile {
115 CallStackProfile(); 145 CallStackProfile();
116 CallStackProfile(const CallStackProfile& other); 146 CallStackProfile(const CallStackProfile& other);
117 ~CallStackProfile(); 147 ~CallStackProfile();
118 148
119 std::vector<Module> modules; 149 std::vector<Module> modules;
120 std::vector<Sample> samples; 150 std::vector<Sample> samples;
121 151
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
154 // The callback type used to collect completed profiles. 184 // The callback type used to collect completed profiles.
155 // 185 //
156 // IMPORTANT NOTE: the callback is invoked on a thread the profiler 186 // IMPORTANT NOTE: the callback is invoked on a thread the profiler
157 // constructs, rather than on the thread used to construct the profiler and 187 // constructs, rather than on the thread used to construct the profiler and
158 // set the callback, and thus the callback must be callable on any thread. For 188 // set the callback, and thus the callback must be callable on any thread. For
159 // threads with message loops that create StackSamplingProfilers, posting a 189 // threads with message loops that create StackSamplingProfilers, posting a
160 // task to the message loop with a copy of the profiles is the recommended 190 // task to the message loop with a copy of the profiles is the recommended
161 // thread-safe callback implementation. 191 // thread-safe callback implementation.
162 using CompletedCallback = Callback<void(const CallStackProfiles&)>; 192 using CompletedCallback = Callback<void(const CallStackProfiles&)>;
163 193
194 // The callback type used to add annotations to a sample during collection.
195 // This is passed to the native sampler to be applied at the most appropriate
196 // time.
197 using AnnotateCallback = Callback<void(Sample*)>;
Mike Wittman 2016/10/26 16:28:17 I think this type would be better on NativeStackSa
198
164 // Creates a profiler that sends completed profiles to |callback|. The second 199 // Creates a profiler that sends completed profiles to |callback|. The second
165 // constructor is for test purposes. 200 // constructor is for test purposes.
166 StackSamplingProfiler(PlatformThreadId thread_id, 201 StackSamplingProfiler(PlatformThreadId thread_id,
167 const SamplingParams& params, 202 const SamplingParams& params,
168 const CompletedCallback& callback); 203 const CompletedCallback& callback);
169 StackSamplingProfiler(PlatformThreadId thread_id, 204 StackSamplingProfiler(PlatformThreadId thread_id,
170 const SamplingParams& params, 205 const SamplingParams& params,
171 const CompletedCallback& callback, 206 const CompletedCallback& callback,
172 NativeStackSamplerTestDelegate* test_delegate); 207 NativeStackSamplerTestDelegate* test_delegate);
173 // Stops any profiling currently taking place before destroying the profiler. 208 // Stops any profiling currently taking place before destroying the profiler.
174 ~StackSamplingProfiler(); 209 ~StackSamplingProfiler();
175 210
176 // The fire-and-forget interface: starts a profiler and allows it to complete 211 // The fire-and-forget interface: starts a profiler and allows it to complete
177 // without the caller needing to manage the profiler lifetime. May be invoked 212 // without the caller needing to manage the profiler lifetime. May be invoked
178 // from any thread, but requires that the calling thread has a message loop. 213 // from any thread, but requires that the calling thread has a message loop.
179 static void StartAndRunAsync(PlatformThreadId thread_id, 214 static void StartAndRunAsync(PlatformThreadId thread_id,
180 const SamplingParams& params, 215 const SamplingParams& params,
181 const CompletedCallback& callback); 216 const CompletedCallback& callback);
182 217
183 // Initializes the profiler and starts sampling. 218 // Initializes the profiler and starts sampling.
184 void Start(); 219 void Start();
185 220
186 // Stops the profiler and any ongoing sampling. Calling this function is 221 // Stops the profiler and any ongoing sampling. Calling this function is
187 // optional; if not invoked profiling terminates when all the profiling bursts 222 // optional; if not invoked profiling terminates when all the profiling bursts
188 // specified in the SamplingParams are completed or the profiler is destroyed, 223 // specified in the SamplingParams are completed or the profiler is destroyed,
189 // whichever occurs first. 224 // whichever occurs first.
190 void Stop(); 225 void Stop();
191 226
227 // Set the current system state that is recorded with each captured stack
228 // frame. These are all thread-safe so can be called from anywhere.
229 static void SetProcessPhase(ProcessPhase phase);
230 static void RecordActivityBegin(ProcessActivity activity);
231 static void RecordActivityEnd(ProcessActivity activity);
232
192 private: 233 private:
193 // SamplingThread is a separate thread used to suspend and sample stacks from 234 // SamplingThread is a separate thread used to suspend and sample stacks from
194 // the target thread. 235 // the target thread.
195 class SamplingThread : public PlatformThread::Delegate { 236 class SamplingThread : public PlatformThread::Delegate {
196 public: 237 public:
197 // Samples stacks using |native_sampler|. When complete, invokes 238 // Samples stacks using |native_sampler|. When complete, invokes
198 // |completed_callback| with the collected call stack profiles. 239 // |completed_callback| with the collected call stack profiles.
199 // |completed_callback| must be callable on any thread. 240 // |completed_callback| must be callable on any thread.
200 SamplingThread(std::unique_ptr<NativeStackSampler> native_sampler, 241 SamplingThread(std::unique_ptr<NativeStackSampler> native_sampler,
201 const SamplingParams& params, 242 const SamplingParams& params,
(...skipping 22 matching lines...) Expand all
224 265
225 // If Stop() is called, it signals this event to force the sampling to 266 // If Stop() is called, it signals this event to force the sampling to
226 // terminate before all the samples specified in |params_| are collected. 267 // terminate before all the samples specified in |params_| are collected.
227 WaitableEvent stop_event_; 268 WaitableEvent stop_event_;
228 269
229 const CompletedCallback completed_callback_; 270 const CompletedCallback completed_callback_;
230 271
231 DISALLOW_COPY_AND_ASSIGN(SamplingThread); 272 DISALLOW_COPY_AND_ASSIGN(SamplingThread);
232 }; 273 };
233 274
275 // Adds "phases" and "activities" annotations to a Sample.
276 static void RecordAnnotations(Sample* sample);
277
278 // These global variables hold current system state. These values are
279 // recorded with every captured sample, done on a separate thread which is
280 // why updates to these must be atomic. A PostTask to move the the updates
281 // to that thread would skew the timing and a lock could result in deadlock
282 // if the thread making a change was also being profiled and got stopped.
283 static subtle::Atomic32 process_phases_;
284 static subtle::Atomic32 current_activities_;
285
234 // The thread whose stack will be sampled. 286 // The thread whose stack will be sampled.
235 PlatformThreadId thread_id_; 287 PlatformThreadId thread_id_;
236 288
237 const SamplingParams params_; 289 const SamplingParams params_;
238 290
239 std::unique_ptr<SamplingThread> sampling_thread_; 291 std::unique_ptr<SamplingThread> sampling_thread_;
240 PlatformThreadHandle sampling_thread_handle_; 292 PlatformThreadHandle sampling_thread_handle_;
241 293
242 const CompletedCallback completed_callback_; 294 const CompletedCallback completed_callback_;
243 295
244 // Stored until it can be passed to the NativeStackSampler created in Start(). 296 // Stored until it can be passed to the NativeStackSampler created in Start().
245 NativeStackSamplerTestDelegate* const test_delegate_; 297 NativeStackSamplerTestDelegate* const test_delegate_;
246 298
247 DISALLOW_COPY_AND_ASSIGN(StackSamplingProfiler); 299 DISALLOW_COPY_AND_ASSIGN(StackSamplingProfiler);
248 }; 300 };
249 301
250 // These operators permit types to be compared and used in a map of Samples, as 302 // These operators permit types to be compared and used in a map of Samples, as
251 // done in tests and by the metrics provider code. 303 // done in tests and by the metrics provider code.
252 BASE_EXPORT bool operator==(const StackSamplingProfiler::Module& a, 304 BASE_EXPORT bool operator==(const StackSamplingProfiler::Module& a,
253 const StackSamplingProfiler::Module& b); 305 const StackSamplingProfiler::Module& b);
306 BASE_EXPORT bool operator==(const StackSamplingProfiler::Sample& a,
307 const StackSamplingProfiler::Sample& b);
308 BASE_EXPORT bool operator!=(const StackSamplingProfiler::Sample& a,
309 const StackSamplingProfiler::Sample& b);
310 BASE_EXPORT bool operator<(const StackSamplingProfiler::Sample& a,
311 const StackSamplingProfiler::Sample& b);
254 BASE_EXPORT bool operator==(const StackSamplingProfiler::Frame& a, 312 BASE_EXPORT bool operator==(const StackSamplingProfiler::Frame& a,
255 const StackSamplingProfiler::Frame& b); 313 const StackSamplingProfiler::Frame& b);
256 BASE_EXPORT bool operator<(const StackSamplingProfiler::Frame& a, 314 BASE_EXPORT bool operator<(const StackSamplingProfiler::Frame& a,
257 const StackSamplingProfiler::Frame& b); 315 const StackSamplingProfiler::Frame& b);
258 316
259 } // namespace base 317 } // namespace base
260 318
261 #endif // BASE_PROFILER_STACK_SAMPLING_PROFILER_H_ 319 #endif // BASE_PROFILER_STACK_SAMPLING_PROFILER_H_
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698