OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project 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 V8_COUNTERS_H_ | 5 #ifndef V8_COUNTERS_H_ |
6 #define V8_COUNTERS_H_ | 6 #define V8_COUNTERS_H_ |
7 | 7 |
8 #include "include/v8.h" | 8 #include "include/v8.h" |
9 #include "src/allocation.h" | 9 #include "src/allocation.h" |
10 #include "src/base/atomic-utils.h" | 10 #include "src/base/atomic-utils.h" |
(...skipping 11 matching lines...) Expand all Loading... |
22 namespace internal { | 22 namespace internal { |
23 | 23 |
24 // StatsCounters is an interface for plugging into external | 24 // StatsCounters is an interface for plugging into external |
25 // counters for monitoring. Counters can be looked up and | 25 // counters for monitoring. Counters can be looked up and |
26 // manipulated by name. | 26 // manipulated by name. |
27 | 27 |
28 class Counters; | 28 class Counters; |
29 | 29 |
30 class StatsTable { | 30 class StatsTable { |
31 public: | 31 public: |
32 // Register an application-defined function where | 32 // Register an application-defined function for recording |
33 // counters can be looked up. Note: Must be called on main thread, | 33 // subsequent counter statistics. |
34 // so that threaded stats counters can be created now. | |
35 void SetCounterFunction(CounterLookupCallback f); | 34 void SetCounterFunction(CounterLookupCallback f); |
36 | 35 |
37 // Register an application-defined function to create | 36 // Register an application-defined function to create histograms for |
38 // a histogram for passing to the AddHistogramSample function | 37 // recording subsequent histogram samples. |
39 void SetCreateHistogramFunction(CreateHistogramCallback f) { | 38 void SetCreateHistogramFunction(CreateHistogramCallback f) { |
40 create_histogram_function_ = f; | 39 create_histogram_function_ = f; |
41 } | 40 } |
42 | 41 |
43 // Register an application-defined function to add a sample | 42 // Register an application-defined function to add a sample |
44 // to a histogram created with CreateHistogram function | 43 // to a histogram created with CreateHistogram function. |
45 void SetAddHistogramSampleFunction(AddHistogramSampleCallback f) { | 44 void SetAddHistogramSampleFunction(AddHistogramSampleCallback f) { |
46 add_histogram_sample_function_ = f; | 45 add_histogram_sample_function_ = f; |
47 } | 46 } |
48 | 47 |
49 bool HasCounterFunction() const { | 48 bool HasCounterFunction() const { |
50 return lookup_function_ != NULL; | 49 return lookup_function_ != NULL; |
51 } | 50 } |
52 | 51 |
53 // Lookup the location of a counter by name. If the lookup | 52 // Lookup the location of a counter by name. If the lookup |
54 // is successful, returns a non-NULL pointer for writing the | 53 // is successful, returns a non-NULL pointer for writing the |
(...skipping 20 matching lines...) Expand all Loading... |
75 } | 74 } |
76 | 75 |
77 // Add a sample to a histogram created with the CreateHistogram | 76 // Add a sample to a histogram created with the CreateHistogram |
78 // function. | 77 // function. |
79 void AddHistogramSample(void* histogram, int sample) { | 78 void AddHistogramSample(void* histogram, int sample) { |
80 if (!add_histogram_sample_function_) return; | 79 if (!add_histogram_sample_function_) return; |
81 return add_histogram_sample_function_(histogram, sample); | 80 return add_histogram_sample_function_(histogram, sample); |
82 } | 81 } |
83 | 82 |
84 private: | 83 private: |
| 84 friend class Counters; |
| 85 |
85 explicit StatsTable(Counters* counters); | 86 explicit StatsTable(Counters* counters); |
86 | 87 |
87 Counters* counters_; | |
88 CounterLookupCallback lookup_function_; | 88 CounterLookupCallback lookup_function_; |
89 CreateHistogramCallback create_histogram_function_; | 89 CreateHistogramCallback create_histogram_function_; |
90 AddHistogramSampleCallback add_histogram_sample_function_; | 90 AddHistogramSampleCallback add_histogram_sample_function_; |
91 | 91 |
92 friend class Counters; | |
93 | |
94 DISALLOW_COPY_AND_ASSIGN(StatsTable); | 92 DISALLOW_COPY_AND_ASSIGN(StatsTable); |
95 }; | 93 }; |
96 | 94 |
97 // Base class for stats counters. | 95 // Base class for stats counters. |
98 class StatsCounterBase { | 96 class StatsCounterBase { |
99 protected: | 97 protected: |
100 Counters* counters_; | 98 Counters* counters_; |
101 const char* name_; | 99 const char* name_; |
102 int* ptr_; | 100 int* ptr_; |
103 | 101 |
(...skipping 10 matching lines...) Expand all Loading... |
114 int* FindLocationInStatsTable() const; | 112 int* FindLocationInStatsTable() const; |
115 }; | 113 }; |
116 | 114 |
117 // StatsCounters are dynamically created values which can be tracked in | 115 // StatsCounters are dynamically created values which can be tracked in |
118 // the StatsTable. They are designed to be lightweight to create and | 116 // the StatsTable. They are designed to be lightweight to create and |
119 // easy to use. | 117 // easy to use. |
120 // | 118 // |
121 // Internally, a counter represents a value in a row of a StatsTable. | 119 // Internally, a counter represents a value in a row of a StatsTable. |
122 // The row has a 32bit value for each process/thread in the table and also | 120 // The row has a 32bit value for each process/thread in the table and also |
123 // a name (stored in the table metadata). Since the storage location can be | 121 // a name (stored in the table metadata). Since the storage location can be |
124 // thread-specific, this class cannot be shared across threads. | 122 // thread-specific, this class cannot be shared across threads. Note: This |
| 123 // class is not thread safe. |
125 class StatsCounter : public StatsCounterBase { | 124 class StatsCounter : public StatsCounterBase { |
126 public: | 125 public: |
127 StatsCounter() { } | |
128 StatsCounter(Counters* counters, const char* name) | |
129 : StatsCounterBase(counters, name), lookup_done_(false) {} | |
130 | |
131 // Sets the counter to a specific value. | 126 // Sets the counter to a specific value. |
132 void Set(int value) { | 127 void Set(int value) { |
133 if (int* loc = GetPtr()) SetLoc(loc, value); | 128 if (int* loc = GetPtr()) SetLoc(loc, value); |
134 } | 129 } |
135 | 130 |
136 // Increments the counter. | 131 // Increments the counter. |
137 void Increment() { | 132 void Increment() { |
138 if (int* loc = GetPtr()) IncrementLoc(loc); | 133 if (int* loc = GetPtr()) IncrementLoc(loc); |
139 } | 134 } |
140 | 135 |
(...skipping 18 matching lines...) Expand all Loading... |
159 | 154 |
160 // Get the internal pointer to the counter. This is used | 155 // Get the internal pointer to the counter. This is used |
161 // by the code generator to emit code that manipulates a | 156 // by the code generator to emit code that manipulates a |
162 // given counter without calling the runtime system. | 157 // given counter without calling the runtime system. |
163 int* GetInternalPointer() { | 158 int* GetInternalPointer() { |
164 int* loc = GetPtr(); | 159 int* loc = GetPtr(); |
165 DCHECK(loc != NULL); | 160 DCHECK(loc != NULL); |
166 return loc; | 161 return loc; |
167 } | 162 } |
168 | 163 |
| 164 private: |
| 165 friend class Counters; |
| 166 |
| 167 StatsCounter() {} |
| 168 StatsCounter(Counters* counters, const char* name) |
| 169 : StatsCounterBase(counters, name), lookup_done_(false) {} |
| 170 |
169 // Reset the cached internal pointer. | 171 // Reset the cached internal pointer. |
170 void Reset() { lookup_done_ = false; } | 172 void Reset() { lookup_done_ = false; } |
171 | 173 |
172 private: | |
173 // Returns the cached address of this counter location. | 174 // Returns the cached address of this counter location. |
174 int* GetPtr() { | 175 int* GetPtr() { |
175 if (lookup_done_) return ptr_; | 176 if (lookup_done_) return ptr_; |
176 lookup_done_ = true; | 177 lookup_done_ = true; |
177 ptr_ = FindLocationInStatsTable(); | 178 ptr_ = FindLocationInStatsTable(); |
178 return ptr_; | 179 return ptr_; |
179 } | 180 } |
180 | 181 |
181 bool lookup_done_; | 182 bool lookup_done_; |
182 }; | 183 }; |
183 | 184 |
184 // Thread safe version of StatsCounter. WARNING: Unlike StatsCounter, | 185 // Thread safe version of StatsCounter. |
185 // StatsCounterThreadSafe's constructor and method Reset() actually do | |
186 // the table lookup, and should be called from the main thread | |
187 // (i.e. not workers). | |
188 class StatsCounterThreadSafe : public StatsCounterBase { | 186 class StatsCounterThreadSafe : public StatsCounterBase { |
189 public: | 187 public: |
190 StatsCounterThreadSafe(Counters* counters, const char* name); | |
191 | |
192 void Set(int Value); | 188 void Set(int Value); |
193 void Increment(); | 189 void Increment(); |
194 void Increment(int value); | 190 void Increment(int value); |
195 void Decrement(); | 191 void Decrement(); |
196 void Decrement(int value); | 192 void Decrement(int value); |
197 bool Enabled() { return ptr_ != NULL; } | 193 bool Enabled() { return ptr_ != NULL; } |
198 int* GetInternalPointer() { | 194 int* GetInternalPointer() { |
199 DCHECK(ptr_ != NULL); | 195 DCHECK(ptr_ != NULL); |
200 return ptr_; | 196 return ptr_; |
201 } | 197 } |
202 void Reset() { GetPtr(); } | |
203 | 198 |
204 private: | 199 private: |
205 int* GetPtr(); | 200 friend class Counters; |
| 201 |
| 202 StatsCounterThreadSafe(Counters* counters, const char* name); |
| 203 void Reset() { ptr_ = FindLocationInStatsTable(); } |
206 | 204 |
207 base::Mutex mutex_; | 205 base::Mutex mutex_; |
208 | 206 |
209 private: | |
210 DISALLOW_IMPLICIT_CONSTRUCTORS(StatsCounterThreadSafe); | 207 DISALLOW_IMPLICIT_CONSTRUCTORS(StatsCounterThreadSafe); |
211 }; | 208 }; |
212 | 209 |
213 // A Histogram represents a dynamically created histogram in the StatsTable. | 210 // A Histogram represents a dynamically created histogram in the |
214 // It will be registered with the histogram system on first use. | 211 // StatsTable. Note: This class is thread safe. |
215 class Histogram { | 212 class Histogram { |
216 public: | 213 public: |
217 Histogram() { } | 214 // Add a single sample to this histogram. |
| 215 void AddSample(int sample); |
| 216 |
| 217 // Returns true if this histogram is enabled. |
| 218 bool Enabled() { return histogram_ != nullptr; } |
| 219 |
| 220 const char* name() { return name_; } |
| 221 |
| 222 protected: |
| 223 Histogram() {} |
218 Histogram(const char* name, int min, int max, int num_buckets, | 224 Histogram(const char* name, int min, int max, int num_buckets, |
219 Counters* counters) | 225 Counters* counters) |
220 : name_(name), | 226 : name_(name), |
221 min_(min), | 227 min_(min), |
222 max_(max), | 228 max_(max), |
223 num_buckets_(num_buckets), | 229 num_buckets_(num_buckets), |
224 histogram_(NULL), | 230 histogram_(nullptr), |
225 lookup_done_(false), | |
226 counters_(counters) {} | 231 counters_(counters) {} |
227 | 232 |
228 // Add a single sample to this histogram. | |
229 void AddSample(int sample); | |
230 | |
231 // Returns true if this histogram is enabled. | |
232 bool Enabled() { | |
233 return GetHistogram() != NULL; | |
234 } | |
235 | |
236 // Reset the cached internal pointer. | |
237 void Reset() { | |
238 lookup_done_ = false; | |
239 } | |
240 | |
241 const char* name() { return name_; } | |
242 | |
243 protected: | |
244 // Returns the handle to the histogram. | |
245 void* GetHistogram() { | |
246 if (!lookup_done_) { | |
247 lookup_done_ = true; | |
248 histogram_ = CreateHistogram(); | |
249 } | |
250 return histogram_; | |
251 } | |
252 | |
253 Counters* counters() const { return counters_; } | 233 Counters* counters() const { return counters_; } |
254 | 234 |
| 235 // Reset the cached internal pointer. |
| 236 void Reset() { histogram_ = CreateHistogram(); } |
| 237 |
255 private: | 238 private: |
| 239 friend class Counters; |
| 240 |
256 void* CreateHistogram() const; | 241 void* CreateHistogram() const; |
257 | 242 |
258 const char* name_; | 243 const char* name_; |
259 int min_; | 244 int min_; |
260 int max_; | 245 int max_; |
261 int num_buckets_; | 246 int num_buckets_; |
262 void* histogram_; | 247 void* histogram_; |
263 bool lookup_done_; | |
264 Counters* counters_; | 248 Counters* counters_; |
265 }; | 249 }; |
266 | 250 |
267 // A HistogramTimer allows distributions of results to be created. | 251 // A HistogramTimer allows distributions of results to be created. |
268 class HistogramTimer : public Histogram { | 252 class HistogramTimer : public Histogram { |
269 public: | 253 public: |
270 enum Resolution { | 254 enum Resolution { |
271 MILLISECOND, | 255 MILLISECOND, |
272 MICROSECOND | 256 MICROSECOND |
273 }; | 257 }; |
274 | 258 |
275 HistogramTimer() {} | 259 // Note: public for testing purposes only. |
276 HistogramTimer(const char* name, int min, int max, Resolution resolution, | 260 HistogramTimer(const char* name, int min, int max, Resolution resolution, |
277 int num_buckets, Counters* counters) | 261 int num_buckets, Counters* counters) |
278 : Histogram(name, min, max, num_buckets, counters), | 262 : Histogram(name, min, max, num_buckets, counters), |
279 resolution_(resolution) {} | 263 resolution_(resolution) {} |
280 | 264 |
281 // Start the timer. | 265 // Start the timer. |
282 void Start(); | 266 void Start(); |
283 | 267 |
284 // Stop the timer and record the results. | 268 // Stop the timer and record the results. |
285 void Stop(); | 269 void Stop(); |
286 | 270 |
287 // Returns true if the timer is running. | 271 // Returns true if the timer is running. |
288 bool Running() { | 272 bool Running() { |
289 return Enabled() && timer_.IsStarted(); | 273 return Enabled() && timer_.IsStarted(); |
290 } | 274 } |
291 | 275 |
292 // TODO(bmeurer): Remove this when HistogramTimerScope is fixed. | 276 // TODO(bmeurer): Remove this when HistogramTimerScope is fixed. |
293 #ifdef DEBUG | 277 #ifdef DEBUG |
294 base::ElapsedTimer* timer() { return &timer_; } | 278 base::ElapsedTimer* timer() { return &timer_; } |
295 #endif | 279 #endif |
296 | 280 |
297 private: | 281 private: |
| 282 friend class Counters; |
| 283 |
298 base::ElapsedTimer timer_; | 284 base::ElapsedTimer timer_; |
299 Resolution resolution_; | 285 Resolution resolution_; |
| 286 |
| 287 HistogramTimer() {} |
300 }; | 288 }; |
301 | 289 |
302 // Helper class for scoping a HistogramTimer. | 290 // Helper class for scoping a HistogramTimer. |
303 // TODO(bmeurer): The ifdeffery is an ugly hack around the fact that the | 291 // TODO(bmeurer): The ifdeffery is an ugly hack around the fact that the |
304 // Parser is currently reentrant (when it throws an error, we call back | 292 // Parser is currently reentrant (when it throws an error, we call back |
305 // into JavaScript and all bets are off), but ElapsedTimer is not | 293 // into JavaScript and all bets are off), but ElapsedTimer is not |
306 // reentry-safe. Fix this properly and remove |allow_nesting|. | 294 // reentry-safe. Fix this properly and remove |allow_nesting|. |
307 class HistogramTimerScope BASE_EMBEDDED { | 295 class HistogramTimerScope BASE_EMBEDDED { |
308 public: | 296 public: |
309 explicit HistogramTimerScope(HistogramTimer* timer, | 297 explicit HistogramTimerScope(HistogramTimer* timer, |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
348 // An example use might be to aggregate the time spent in lazy compilation | 336 // An example use might be to aggregate the time spent in lazy compilation |
349 // while running a script. | 337 // while running a script. |
350 // | 338 // |
351 // Helpers: | 339 // Helpers: |
352 // - AggregatingHistogramTimerScope, the "outer" scope within which | 340 // - AggregatingHistogramTimerScope, the "outer" scope within which |
353 // times will be summed up. | 341 // times will be summed up. |
354 // - AggregatedHistogramTimerScope, the "inner" scope which defines the | 342 // - AggregatedHistogramTimerScope, the "inner" scope which defines the |
355 // events to be timed. | 343 // events to be timed. |
356 class AggregatableHistogramTimer : public Histogram { | 344 class AggregatableHistogramTimer : public Histogram { |
357 public: | 345 public: |
358 AggregatableHistogramTimer() {} | |
359 AggregatableHistogramTimer(const char* name, int min, int max, | |
360 int num_buckets, Counters* counters) | |
361 : Histogram(name, min, max, num_buckets, counters) {} | |
362 | |
363 // Start/stop the "outer" scope. | 346 // Start/stop the "outer" scope. |
364 void Start() { time_ = base::TimeDelta(); } | 347 void Start() { time_ = base::TimeDelta(); } |
365 void Stop() { AddSample(static_cast<int>(time_.InMicroseconds())); } | 348 void Stop() { AddSample(static_cast<int>(time_.InMicroseconds())); } |
366 | 349 |
367 // Add a time value ("inner" scope). | 350 // Add a time value ("inner" scope). |
368 void Add(base::TimeDelta other) { time_ += other; } | 351 void Add(base::TimeDelta other) { time_ += other; } |
369 | 352 |
370 private: | 353 private: |
| 354 friend class Counters; |
| 355 |
| 356 AggregatableHistogramTimer() {} |
| 357 AggregatableHistogramTimer(const char* name, int min, int max, |
| 358 int num_buckets, Counters* counters) |
| 359 : Histogram(name, min, max, num_buckets, counters) {} |
| 360 |
371 base::TimeDelta time_; | 361 base::TimeDelta time_; |
372 }; | 362 }; |
373 | 363 |
374 // A helper class for use with AggregatableHistogramTimer. This is the | 364 // A helper class for use with AggregatableHistogramTimer. This is the |
375 // // outer-most timer scope used with an AggregatableHistogramTimer. It will | 365 // // outer-most timer scope used with an AggregatableHistogramTimer. It will |
376 // // aggregate the information from the inner AggregatedHistogramTimerScope. | 366 // // aggregate the information from the inner AggregatedHistogramTimerScope. |
377 class AggregatingHistogramTimerScope { | 367 class AggregatingHistogramTimerScope { |
378 public: | 368 public: |
379 explicit AggregatingHistogramTimerScope(AggregatableHistogramTimer* histogram) | 369 explicit AggregatingHistogramTimerScope(AggregatableHistogramTimer* histogram) |
380 : histogram_(histogram) { | 370 : histogram_(histogram) { |
(...skipping 26 matching lines...) Expand all Loading... |
407 // backing histogram receives one sample every T ms, where the T is controlled | 397 // backing histogram receives one sample every T ms, where the T is controlled |
408 // by the FLAG_histogram_interval. | 398 // by the FLAG_histogram_interval. |
409 // | 399 // |
410 // More formally: let F be a real-valued function that maps time to sample | 400 // More formally: let F be a real-valued function that maps time to sample |
411 // values. We define F as a linear interpolation between adjacent samples. For | 401 // values. We define F as a linear interpolation between adjacent samples. For |
412 // each time interval [x; x + T) the backing histogram gets one sample value | 402 // each time interval [x; x + T) the backing histogram gets one sample value |
413 // that is the average of F(t) in the interval. | 403 // that is the average of F(t) in the interval. |
414 template <typename Histogram> | 404 template <typename Histogram> |
415 class AggregatedMemoryHistogram { | 405 class AggregatedMemoryHistogram { |
416 public: | 406 public: |
417 AggregatedMemoryHistogram() | 407 // Note: public for testing purposes only. |
418 : is_initialized_(false), | |
419 start_ms_(0.0), | |
420 last_ms_(0.0), | |
421 aggregate_value_(0.0), | |
422 last_value_(0.0), | |
423 backing_histogram_(NULL) {} | |
424 | |
425 explicit AggregatedMemoryHistogram(Histogram* backing_histogram) | 408 explicit AggregatedMemoryHistogram(Histogram* backing_histogram) |
426 : AggregatedMemoryHistogram() { | 409 : AggregatedMemoryHistogram() { |
427 backing_histogram_ = backing_histogram; | 410 backing_histogram_ = backing_histogram; |
428 } | 411 } |
429 | 412 |
430 // Invariants that hold before and after AddSample if | 413 // Invariants that hold before and after AddSample if |
431 // is_initialized_ is true: | 414 // is_initialized_ is true: |
432 // | 415 // |
433 // 1) For we processed samples that came in before start_ms_ and sent the | 416 // 1) For we processed samples that came in before start_ms_ and sent the |
434 // corresponding aggregated samples to backing histogram. | 417 // corresponding aggregated samples to backing histogram. |
435 // 2) (last_ms_, last_value_) is the last received sample. | 418 // 2) (last_ms_, last_value_) is the last received sample. |
436 // 3) last_ms_ < start_ms_ + FLAG_histogram_interval. | 419 // 3) last_ms_ < start_ms_ + FLAG_histogram_interval. |
437 // 4) aggregate_value_ is the average of the function that is constructed by | 420 // 4) aggregate_value_ is the average of the function that is constructed by |
438 // linearly interpolating samples received between start_ms_ and last_ms_. | 421 // linearly interpolating samples received between start_ms_ and last_ms_. |
439 void AddSample(double current_ms, double current_value); | 422 void AddSample(double current_ms, double current_value); |
440 | 423 |
441 private: | 424 private: |
| 425 friend class Counters; |
| 426 |
| 427 AggregatedMemoryHistogram() |
| 428 : is_initialized_(false), |
| 429 start_ms_(0.0), |
| 430 last_ms_(0.0), |
| 431 aggregate_value_(0.0), |
| 432 last_value_(0.0), |
| 433 backing_histogram_(NULL) {} |
442 double Aggregate(double current_ms, double current_value); | 434 double Aggregate(double current_ms, double current_value); |
| 435 |
443 bool is_initialized_; | 436 bool is_initialized_; |
444 double start_ms_; | 437 double start_ms_; |
445 double last_ms_; | 438 double last_ms_; |
446 double aggregate_value_; | 439 double aggregate_value_; |
447 double last_value_; | 440 double last_value_; |
448 Histogram* backing_histogram_; | 441 Histogram* backing_histogram_; |
449 }; | 442 }; |
450 | 443 |
451 | 444 |
452 template <typename Histogram> | 445 template <typename Histogram> |
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
529 | 522 |
530 const char* name() const { return name_; } | 523 const char* name() const { return name_; } |
531 int64_t count() const { return count_; } | 524 int64_t count() const { return count_; } |
532 base::TimeDelta time() const { | 525 base::TimeDelta time() const { |
533 return base::TimeDelta::FromMicroseconds(time_); | 526 return base::TimeDelta::FromMicroseconds(time_); |
534 } | 527 } |
535 void Increment() { count_++; } | 528 void Increment() { count_++; } |
536 void Add(base::TimeDelta delta) { time_ += delta.InMicroseconds(); } | 529 void Add(base::TimeDelta delta) { time_ += delta.InMicroseconds(); } |
537 | 530 |
538 private: | 531 private: |
| 532 friend class RuntimeCallStats; |
| 533 |
539 RuntimeCallCounter() {} | 534 RuntimeCallCounter() {} |
540 | 535 |
541 const char* name_; | 536 const char* name_; |
542 int64_t count_; | 537 int64_t count_; |
543 // Stored as int64_t so that its initialization can be deferred. | 538 // Stored as int64_t so that its initialization can be deferred. |
544 int64_t time_; | 539 int64_t time_; |
545 | |
546 friend class RuntimeCallStats; | |
547 }; | 540 }; |
548 | 541 |
549 // RuntimeCallTimer is used to keep track of the stack of currently active | 542 // RuntimeCallTimer is used to keep track of the stack of currently active |
550 // timers used for properly measuring the own time of a RuntimeCallCounter. | 543 // timers used for properly measuring the own time of a RuntimeCallCounter. |
551 class RuntimeCallTimer final { | 544 class RuntimeCallTimer final { |
552 public: | 545 public: |
553 RuntimeCallCounter* counter() { return counter_; } | 546 RuntimeCallCounter* counter() { return counter_; } |
554 void set_counter(RuntimeCallCounter* counter) { counter_ = counter; } | 547 void set_counter(RuntimeCallCounter* counter) { counter_ = counter; } |
555 RuntimeCallTimer* parent() const { return parent_.Value(); } | 548 RuntimeCallTimer* parent() const { return parent_.Value(); } |
556 void set_parent(RuntimeCallTimer* timer) { parent_.SetValue(timer); } | 549 void set_parent(RuntimeCallTimer* timer) { parent_.SetValue(timer); } |
(...skipping 653 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1210 #define STATS_COUNTER_TS_LIST(SC) \ | 1203 #define STATS_COUNTER_TS_LIST(SC) \ |
1211 SC(wasm_generated_code_size, V8.WasmGeneratedCodeBytes) \ | 1204 SC(wasm_generated_code_size, V8.WasmGeneratedCodeBytes) \ |
1212 SC(wasm_reloc_size, V8.WasmRelocBytes) \ | 1205 SC(wasm_reloc_size, V8.WasmRelocBytes) \ |
1213 SC(wasm_lazily_compiled_functions, V8.WasmLazilyCompiledFunctions) | 1206 SC(wasm_lazily_compiled_functions, V8.WasmLazilyCompiledFunctions) |
1214 | 1207 |
1215 // This file contains all the v8 counters that are in use. | 1208 // This file contains all the v8 counters that are in use. |
1216 class Counters : public std::enable_shared_from_this<Counters> { | 1209 class Counters : public std::enable_shared_from_this<Counters> { |
1217 public: | 1210 public: |
1218 explicit Counters(Isolate* isolate); | 1211 explicit Counters(Isolate* isolate); |
1219 | 1212 |
| 1213 // Register an application-defined function for recording |
| 1214 // subsequent counter statistics. Note: Must be called on the main |
| 1215 // thread. |
| 1216 void ResetCounterFunction(CounterLookupCallback f); |
| 1217 |
| 1218 // Register an application-defined function to create histograms for |
| 1219 // recording subsequent histogram samples. Note: Must be called on |
| 1220 // the main thread. |
| 1221 void ResetCreateHistogramFunction(CreateHistogramCallback f); |
| 1222 |
| 1223 // Register an application-defined function to add a sample |
| 1224 // to a histogram. Will be used in all subsequent sample additions. |
| 1225 // Note: Must be called on the main thread. |
| 1226 void SetAddHistogramSampleFunction(AddHistogramSampleCallback f) { |
| 1227 stats_table_.SetAddHistogramSampleFunction(f); |
| 1228 } |
| 1229 |
1220 #define HR(name, caption, min, max, num_buckets) \ | 1230 #define HR(name, caption, min, max, num_buckets) \ |
1221 Histogram* name() { return &name##_; } | 1231 Histogram* name() { return &name##_; } |
1222 HISTOGRAM_RANGE_LIST(HR) | 1232 HISTOGRAM_RANGE_LIST(HR) |
1223 #undef HR | 1233 #undef HR |
1224 | 1234 |
1225 #define HT(name, caption, max, res) \ | 1235 #define HT(name, caption, max, res) \ |
1226 HistogramTimer* name() { return &name##_; } | 1236 HistogramTimer* name() { return &name##_; } |
1227 HISTOGRAM_TIMER_LIST(HT) | 1237 HISTOGRAM_TIMER_LIST(HT) |
1228 #undef HT | 1238 #undef HT |
1229 | 1239 |
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1323 FIXED_ARRAY_SUB_INSTANCE_TYPE_LIST(COUNTER_ID) | 1333 FIXED_ARRAY_SUB_INSTANCE_TYPE_LIST(COUNTER_ID) |
1324 #undef COUNTER_ID | 1334 #undef COUNTER_ID |
1325 #define COUNTER_ID(name) kCountOfCODE_AGE__##name, \ | 1335 #define COUNTER_ID(name) kCountOfCODE_AGE__##name, \ |
1326 kSizeOfCODE_AGE__##name, | 1336 kSizeOfCODE_AGE__##name, |
1327 CODE_AGE_LIST_COMPLETE(COUNTER_ID) | 1337 CODE_AGE_LIST_COMPLETE(COUNTER_ID) |
1328 #undef COUNTER_ID | 1338 #undef COUNTER_ID |
1329 stats_counter_count | 1339 stats_counter_count |
1330 }; | 1340 }; |
1331 // clang-format on | 1341 // clang-format on |
1332 | 1342 |
1333 void ResetCounters(); | |
1334 void ResetHistograms(); | |
1335 void InitializeHistograms(); | |
1336 | |
1337 RuntimeCallStats* runtime_call_stats() { return &runtime_call_stats_; } | 1343 RuntimeCallStats* runtime_call_stats() { return &runtime_call_stats_; } |
1338 | 1344 |
1339 StatsTable* stats_table() { return &stats_table_; } | 1345 private: |
| 1346 friend class StatsTable; |
| 1347 friend class StatsCounterBase; |
| 1348 friend class Histogram; |
| 1349 friend class HistogramTimer; |
| 1350 |
| 1351 Isolate* isolate_; |
| 1352 StatsTable stats_table_; |
| 1353 |
| 1354 int* FindLocation(const char* name) { |
| 1355 return stats_table_.FindLocation(name); |
| 1356 } |
| 1357 |
| 1358 void* CreateHistogram(const char* name, int min, int max, size_t buckets) { |
| 1359 return stats_table_.CreateHistogram(name, min, max, buckets); |
| 1360 } |
| 1361 |
| 1362 void AddHistogramSample(void* histogram, int sample) { |
| 1363 stats_table_.AddHistogramSample(histogram, sample); |
| 1364 } |
1340 | 1365 |
1341 Isolate* isolate() { return isolate_; } | 1366 Isolate* isolate() { return isolate_; } |
1342 | 1367 |
1343 private: | |
1344 Isolate* isolate_; | |
1345 StatsTable stats_table_; | |
1346 | |
1347 #define HR(name, caption, min, max, num_buckets) Histogram name##_; | 1368 #define HR(name, caption, min, max, num_buckets) Histogram name##_; |
1348 HISTOGRAM_RANGE_LIST(HR) | 1369 HISTOGRAM_RANGE_LIST(HR) |
1349 #undef HR | 1370 #undef HR |
1350 | 1371 |
1351 #define HT(name, caption, max, res) HistogramTimer name##_; | 1372 #define HT(name, caption, max, res) HistogramTimer name##_; |
1352 HISTOGRAM_TIMER_LIST(HT) | 1373 HISTOGRAM_TIMER_LIST(HT) |
1353 #undef HT | 1374 #undef HT |
1354 | 1375 |
1355 #define AHT(name, caption) \ | 1376 #define AHT(name, caption) \ |
1356 AggregatableHistogramTimer name##_; | 1377 AggregatableHistogramTimer name##_; |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1409 | 1430 |
1410 RuntimeCallStats runtime_call_stats_; | 1431 RuntimeCallStats runtime_call_stats_; |
1411 | 1432 |
1412 DISALLOW_IMPLICIT_CONSTRUCTORS(Counters); | 1433 DISALLOW_IMPLICIT_CONSTRUCTORS(Counters); |
1413 }; | 1434 }; |
1414 | 1435 |
1415 } // namespace internal | 1436 } // namespace internal |
1416 } // namespace v8 | 1437 } // namespace v8 |
1417 | 1438 |
1418 #endif // V8_COUNTERS_H_ | 1439 #endif // V8_COUNTERS_H_ |
OLD | NEW |