| 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/platform/elapsed-timer.h" | 10 #include "src/base/platform/elapsed-timer.h" |
| (...skipping 483 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 494 public: | 494 public: |
| 495 RuntimeCallTimer() {} | 495 RuntimeCallTimer() {} |
| 496 | 496 |
| 497 private: | 497 private: |
| 498 friend class RuntimeCallStats; | 498 friend class RuntimeCallStats; |
| 499 | 499 |
| 500 inline void Start(RuntimeCallCounter* counter, RuntimeCallTimer* parent) { | 500 inline void Start(RuntimeCallCounter* counter, RuntimeCallTimer* parent) { |
| 501 counter_ = counter; | 501 counter_ = counter; |
| 502 parent_ = parent; | 502 parent_ = parent; |
| 503 timer_.Start(); | 503 timer_.Start(); |
| 504 counter_->count++; | |
| 505 } | 504 } |
| 506 | 505 |
| 507 inline RuntimeCallTimer* Stop() { | 506 inline RuntimeCallTimer* Stop() { |
| 508 base::TimeDelta delta = timer_.Elapsed(); | 507 base::TimeDelta delta = timer_.Elapsed(); |
| 509 timer_.Stop(); | 508 timer_.Stop(); |
| 509 counter_->count++; |
| 510 counter_->time += delta; | 510 counter_->time += delta; |
| 511 if (parent_ != NULL) { | 511 if (parent_ != NULL) { |
| 512 // Adjust parent timer so that it does not include sub timer's time. | 512 // Adjust parent timer so that it does not include sub timer's time. |
| 513 parent_->counter_->time -= delta; | 513 parent_->counter_->time -= delta; |
| 514 } | 514 } |
| 515 return parent_; | 515 return parent_; |
| 516 } | 516 } |
| 517 | 517 |
| 518 RuntimeCallCounter* counter_ = nullptr; | 518 RuntimeCallCounter* counter_ = nullptr; |
| 519 RuntimeCallTimer* parent_ = nullptr; | 519 RuntimeCallTimer* parent_ = nullptr; |
| 520 base::ElapsedTimer timer_; | 520 base::ElapsedTimer timer_; |
| 521 }; | 521 }; |
| 522 | 522 |
| 523 #define FOR_EACH_HANDLER_COUNTER(V) \ |
| 524 V(IC_HandlerCacheHit) \ |
| 525 V(KeyedLoadIC_LoadIndexedStringStub) \ |
| 526 V(KeyedLoadIC_LoadIndexedInterceptorStub) \ |
| 527 V(KeyedLoadIC_KeyedLoadSloppyArgumentsStub) \ |
| 528 V(KeyedLoadIC_LoadFastElementStub) \ |
| 529 V(KeyedLoadIC_LoadDictionaryElementStub) \ |
| 530 V(KeyedLoadIC_PolymorphicElement) \ |
| 531 V(KeyedStoreIC_KeyedStoreSloppyArgumentsStub) \ |
| 532 V(KeyedStoreIC_StoreFastElementStub) \ |
| 533 V(KeyedStoreIC_StoreElementStub) \ |
| 534 V(KeyedStoreIC_Polymorphic) \ |
| 535 V(LoadIC_FunctionPrototypeStub) \ |
| 536 V(LoadIC_ArrayBufferViewLoadFieldStub) \ |
| 537 V(LoadIC_LoadApiGetterStub) \ |
| 538 V(LoadIC_LoadCallback) \ |
| 539 V(LoadIC_LoadConstant) \ |
| 540 V(LoadIC_LoadConstantStub) \ |
| 541 V(LoadIC_LoadField) \ |
| 542 V(LoadIC_LoadFieldStub) \ |
| 543 V(LoadIC_LoadGlobal) \ |
| 544 V(LoadIC_LoadInterceptor) \ |
| 545 V(LoadIC_LoadNonexistent) \ |
| 546 V(LoadIC_LoadNormal) \ |
| 547 V(LoadIC_LoadScriptContextFieldStub) \ |
| 548 V(LoadIC_LoadViaGetter) \ |
| 549 V(LoadIC_SlowStub) \ |
| 550 V(LoadIC_StringLengthStub) \ |
| 551 V(StoreIC_SlowStub) \ |
| 552 V(StoreIC_StoreCallback) \ |
| 553 V(StoreIC_StoreField) \ |
| 554 V(StoreIC_StoreFieldStub) \ |
| 555 V(StoreIC_StoreGlobal) \ |
| 556 V(StoreIC_StoreGlobalTransition) \ |
| 557 V(StoreIC_StoreInterceptorStub) \ |
| 558 V(StoreIC_StoreNormal) \ |
| 559 V(StoreIC_StoreScriptContextFieldStub) \ |
| 560 V(StoreIC_StoreTransition) \ |
| 561 V(StoreIC_StoreViaSetter) |
| 562 |
| 523 class RuntimeCallStats { | 563 class RuntimeCallStats { |
| 524 public: | 564 public: |
| 525 typedef RuntimeCallCounter RuntimeCallStats::*CounterId; | 565 typedef RuntimeCallCounter RuntimeCallStats::*CounterId; |
| 526 | 566 |
| 527 // Dummy counter for the unexpected stub miss. | 567 // Dummy counter for the unexpected stub miss. |
| 528 RuntimeCallCounter UnexpectedStubMiss = | 568 RuntimeCallCounter UnexpectedStubMiss = |
| 529 RuntimeCallCounter("UnexpectedStubMiss"); | 569 RuntimeCallCounter("UnexpectedStubMiss"); |
| 530 // Counter for runtime callbacks into JavaScript. | 570 // Counter for runtime callbacks into JavaScript. |
| 531 RuntimeCallCounter ExternalCallback = RuntimeCallCounter("ExternalCallback"); | 571 RuntimeCallCounter ExternalCallback = RuntimeCallCounter("ExternalCallback"); |
| 532 RuntimeCallCounter GC = RuntimeCallCounter("GC"); | 572 RuntimeCallCounter GC = RuntimeCallCounter("GC"); |
| 533 #define CALL_RUNTIME_COUNTER(name, nargs, ressize) \ | 573 #define CALL_RUNTIME_COUNTER(name, nargs, ressize) \ |
| 534 RuntimeCallCounter Runtime_##name = RuntimeCallCounter(#name); | 574 RuntimeCallCounter Runtime_##name = RuntimeCallCounter(#name); |
| 535 FOR_EACH_INTRINSIC(CALL_RUNTIME_COUNTER) | 575 FOR_EACH_INTRINSIC(CALL_RUNTIME_COUNTER) |
| 536 #undef CALL_RUNTIME_COUNTER | 576 #undef CALL_RUNTIME_COUNTER |
| 537 #define CALL_BUILTIN_COUNTER(name, type) \ | 577 #define CALL_BUILTIN_COUNTER(name, type) \ |
| 538 RuntimeCallCounter Builtin_##name = RuntimeCallCounter(#name); | 578 RuntimeCallCounter Builtin_##name = RuntimeCallCounter(#name); |
| 539 BUILTIN_LIST_C(CALL_BUILTIN_COUNTER) | 579 BUILTIN_LIST_C(CALL_BUILTIN_COUNTER) |
| 540 #undef CALL_BUILTIN_COUNTER | 580 #undef CALL_BUILTIN_COUNTER |
| 581 #define CALL_BUILTIN_COUNTER(name) \ |
| 582 RuntimeCallCounter Handler_##name = RuntimeCallCounter(#name); |
| 583 FOR_EACH_HANDLER_COUNTER(CALL_BUILTIN_COUNTER) |
| 584 #undef CALL_BUILTIN_COUNTER |
| 541 | 585 |
| 542 // Starting measuring the time for a function. This will establish the | 586 // Starting measuring the time for a function. This will establish the |
| 543 // connection to the parent counter for properly calculating the own times. | 587 // connection to the parent counter for properly calculating the own times. |
| 544 static void Enter(Isolate* isolate, RuntimeCallTimer* timer, | 588 static void Enter(Isolate* isolate, RuntimeCallTimer* timer, |
| 545 CounterId counter_id); | 589 CounterId counter_id); |
| 546 | 590 |
| 547 // Leave a scope for a measured runtime function. This will properly add | 591 // Leave a scope for a measured runtime function. This will properly add |
| 548 // the time delta to the current_counter and subtract the delta from its | 592 // the time delta to the current_counter and subtract the delta from its |
| 549 // parent. | 593 // parent. |
| 550 static void Leave(Isolate* isolate, RuntimeCallTimer* timer); | 594 static void Leave(Isolate* isolate, RuntimeCallTimer* timer); |
| 551 | 595 |
| 596 // Set counter id for the innermost measurement. It can be used to refine |
| 597 // event kind when a runtime entry counter is too generic. |
| 598 static void CorrectCurrentCounterId(Isolate* isolate, CounterId counter_id); |
| 599 |
| 552 void Reset(); | 600 void Reset(); |
| 553 void Print(std::ostream& os); | 601 void Print(std::ostream& os); |
| 554 | 602 |
| 555 RuntimeCallStats() { Reset(); } | 603 RuntimeCallStats() { Reset(); } |
| 556 | 604 |
| 557 private: | 605 private: |
| 558 // Counter to track recursive time events. | 606 // Counter to track recursive time events. |
| 559 RuntimeCallTimer* current_timer_ = NULL; | 607 RuntimeCallTimer* current_timer_ = NULL; |
| 560 }; | 608 }; |
| 561 | 609 |
| 610 #define TRACE_RUNTIME_CALL_STATS(isolate, counter_name) \ |
| 611 do { \ |
| 612 if (FLAG_runtime_call_stats) { \ |
| 613 RuntimeCallStats::CorrectCurrentCounterId( \ |
| 614 isolate, &RuntimeCallStats::counter_name); \ |
| 615 } \ |
| 616 } while (false) |
| 617 |
| 618 #define TRACE_HANDLER_STATS(isolate, counter_name) \ |
| 619 TRACE_RUNTIME_CALL_STATS(isolate, Handler_##counter_name) |
| 620 |
| 562 // A RuntimeCallTimerScopes wraps around a RuntimeCallTimer to measure the | 621 // A RuntimeCallTimerScopes wraps around a RuntimeCallTimer to measure the |
| 563 // the time of C++ scope. | 622 // the time of C++ scope. |
| 564 class RuntimeCallTimerScope { | 623 class RuntimeCallTimerScope { |
| 565 public: | 624 public: |
| 566 inline explicit RuntimeCallTimerScope( | 625 inline explicit RuntimeCallTimerScope( |
| 567 Isolate* isolate, RuntimeCallStats::CounterId counter_id) { | 626 Isolate* isolate, RuntimeCallStats::CounterId counter_id) { |
| 568 if (V8_UNLIKELY(FLAG_runtime_call_stats)) { | 627 if (V8_UNLIKELY(FLAG_runtime_call_stats)) { |
| 569 isolate_ = isolate; | 628 isolate_ = isolate; |
| 570 RuntimeCallStats::Enter(isolate_, &timer_, counter_id); | 629 RuntimeCallStats::Enter(isolate_, &timer_, counter_id); |
| 571 } | 630 } |
| (...skipping 419 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 991 | 1050 |
| 992 explicit Counters(Isolate* isolate); | 1051 explicit Counters(Isolate* isolate); |
| 993 | 1052 |
| 994 DISALLOW_IMPLICIT_CONSTRUCTORS(Counters); | 1053 DISALLOW_IMPLICIT_CONSTRUCTORS(Counters); |
| 995 }; | 1054 }; |
| 996 | 1055 |
| 997 } // namespace internal | 1056 } // namespace internal |
| 998 } // namespace v8 | 1057 } // namespace v8 |
| 999 | 1058 |
| 1000 #endif // V8_COUNTERS_H_ | 1059 #endif // V8_COUNTERS_H_ |
| OLD | NEW |