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

Side by Side Diff: src/log.cc

Issue 6904127: ll_prof: Reduce profiling hooks overhead from >400% to 25%. (Closed)
Patch Set: Created 9 years, 7 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
« no previous file with comments | « src/log.h ('k') | src/log-utils.h » ('j') | src/utils.h » ('J')
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2009 the V8 project authors. All rights reserved. 1 // Copyright 2009 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 316 matching lines...) Expand 10 before | Expand all | Expand 10 after
327 TickSample sample; 327 TickSample sample;
328 bool overflow = Remove(&sample); 328 bool overflow = Remove(&sample);
329 i::Isolate* isolate = ISOLATE; 329 i::Isolate* isolate = ISOLATE;
330 while (running_) { 330 while (running_) {
331 LOG(isolate, TickEvent(&sample, overflow)); 331 LOG(isolate, TickEvent(&sample, overflow));
332 overflow = Remove(&sample); 332 overflow = Remove(&sample);
333 } 333 }
334 } 334 }
335 335
336 336
337 // Low-level profiling event structures.
338
339 struct LowLevelCodeCreateStruct {
340 static const char kTag = 'C';
341
342 int32_t name_size;
343 Address code_address;
344 int32_t code_size;
345 };
346
347
348 struct LowLevelCodeMoveStruct {
349 static const char kTag = 'M';
350
351 Address from_address;
352 Address to_address;
353 };
354
355
356 struct LowLevelCodeDeleteStruct {
357 static const char kTag = 'D';
358
359 Address address;
360 };
361
362
363 struct LowLevelSnapshotPositionStruct {
364 static const char kTag = 'P';
365
366 Address address;
367 int32_t position;
368 };
369
370
371 static const char kCodeMovingGCTag = 'G';
372
373
337 // 374 //
338 // Logger class implementation. 375 // Logger class implementation.
339 // 376 //
340 377
378 class Logger::NameBuffer {
379 public:
380 NameBuffer() { Reset(); }
381
382 void Reset() {
383 utf8_pos_ = 0;
384 }
385
386 void AppendString(String* str) {
387 if (str == NULL) return;
388 if (str->HasOnlyAsciiChars()) {
389 int utf8_length = Min(str->length(), kUtf8BufferSize - utf8_pos_);
390 String::WriteToFlat(str, utf8_buffer_ + utf8_pos_, 0, utf8_length);
391 utf8_pos_ += utf8_length;
392 return;
393 }
394 int uc16_length = Min(str->length(), kUc16BufferSize);
395 String::WriteToFlat(str, uc16_buffer_, 0, uc16_length);
396 for (int i = 0; i < uc16_length && utf8_pos_ < kUtf8BufferSize; ++i) {
397 uc16 c = uc16_buffer_[i];
398 if (c <= String::kMaxAsciiCharCodeU) {
399 utf8_buffer_[utf8_pos_++] = c;
400 } else {
401 int char_length = unibrow::Utf8::Length(c);
402 if (utf8_pos_ + char_length > kUtf8BufferSize) break;
403 unibrow::Utf8::Encode(utf8_buffer_ + utf8_pos_, c);
404 utf8_pos_ += char_length;
405 }
406 }
407 }
408
409 void AppendBytes(const char* bytes, int size) {
410 size = Min(size, kUtf8BufferSize - utf8_pos_);
411 memcpy(utf8_buffer_ + utf8_pos_, bytes, size);
412 utf8_pos_ += size;
413 }
414
415 void AppendBytes(const char* bytes) {
416 AppendBytes(bytes, StrLength(bytes));
417 }
418
419 void AppendByte(char c) {
420 if (utf8_pos_ >= kUtf8BufferSize) return;
421 utf8_buffer_[utf8_pos_++] = c;
422 }
423
424 void AppendInt(int n) {
425 Vector<char> buffer(utf8_buffer_ + utf8_pos_, kUtf8BufferSize - utf8_pos_);
426 int size = OS::SNPrintF(buffer, "%d", n);
427 if (size > 0 && utf8_pos_ + size <= kUtf8BufferSize) {
428 utf8_pos_ += size;
429 }
430 }
431
432 const char* get() { return utf8_buffer_; }
433 int size() const { return utf8_pos_; }
434
435 private:
436 static const int kUtf8BufferSize = 512;
437 static const int kUc16BufferSize = 128;
438
439 int utf8_pos_;
440 char utf8_buffer_[kUtf8BufferSize];
441 uc16 uc16_buffer_[kUc16BufferSize];
442 };
443
444
445 static bool PointerEquals(void* lhs, void* rhs) {
446 return lhs == rhs;
447 }
448
449
341 Logger::Logger() 450 Logger::Logger()
342 : ticker_(NULL), 451 : ticker_(NULL),
343 profiler_(NULL), 452 profiler_(NULL),
344 sliding_state_window_(NULL), 453 sliding_state_window_(NULL),
345 log_events_(NULL), 454 log_events_(NULL),
346 logging_nesting_(0), 455 logging_nesting_(0),
347 cpu_profiler_nesting_(0), 456 cpu_profiler_nesting_(0),
348 heap_profiler_nesting_(0), 457 heap_profiler_nesting_(0),
349 log_(new Log(this)), 458 log_(new Log(this)),
459 name_buffer_(new NameBuffer),
460 address_to_name_map_(NULL),
350 is_initialized_(false), 461 is_initialized_(false),
351 last_address_(NULL), 462 last_address_(NULL),
352 prev_sp_(NULL), 463 prev_sp_(NULL),
353 prev_function_(NULL), 464 prev_function_(NULL),
354 prev_to_(NULL), 465 prev_to_(NULL),
355 prev_code_(NULL) { 466 prev_code_(NULL) {
356 } 467 }
357 468
469
358 Logger::~Logger() { 470 Logger::~Logger() {
471 if (address_to_name_map_ != NULL) {
472 for (HashMap::Entry* p = address_to_name_map_->Start();
473 p != NULL;
474 p = address_to_name_map_->Next(p)) {
475 DeleteArray(static_cast<const char*>(p->value));
476 }
477 delete address_to_name_map_;
478 }
479 delete name_buffer_;
359 delete log_; 480 delete log_;
360 } 481 }
361 482
483
362 #define DECLARE_EVENT(ignore1, name) name, 484 #define DECLARE_EVENT(ignore1, name) name,
363 static const char* const kLogEventsNames[Logger::NUMBER_OF_LOG_EVENTS] = { 485 static const char* const kLogEventsNames[Logger::NUMBER_OF_LOG_EVENTS] = {
364 LOG_EVENTS_AND_TAGS_LIST(DECLARE_EVENT) 486 LOG_EVENTS_AND_TAGS_LIST(DECLARE_EVENT)
365 }; 487 };
366 #undef DECLARE_EVENT 488 #undef DECLARE_EVENT
367 489
368 490
369 void Logger::ProfilerBeginEvent() { 491 void Logger::ProfilerBeginEvent() {
370 if (!log_->IsEnabled()) return; 492 if (!log_->IsEnabled()) return;
371 LogMessageBuilder msg(this); 493 LogMessageBuilder msg(this);
(...skipping 356 matching lines...) Expand 10 before | Expand all | Expand 10 after
728 name->ToCString(DISALLOW_NULLS, ROBUST_STRING_TRAVERSAL); 850 name->ToCString(DISALLOW_NULLS, ROBUST_STRING_TRAVERSAL);
729 CallbackEventInternal("set ", *str, entry_point); 851 CallbackEventInternal("set ", *str, entry_point);
730 #endif 852 #endif
731 } 853 }
732 854
733 855
734 void Logger::CodeCreateEvent(LogEventsAndTags tag, 856 void Logger::CodeCreateEvent(LogEventsAndTags tag,
735 Code* code, 857 Code* code,
736 const char* comment) { 858 const char* comment) {
737 #ifdef ENABLE_LOGGING_AND_PROFILING 859 #ifdef ENABLE_LOGGING_AND_PROFILING
738 if (!log_->IsEnabled() || !FLAG_log_code) return; 860 if (!log_->IsEnabled()) return;
861 if (FLAG_ll_prof || Serializer::enabled()) {
862 name_buffer_->Reset();
863 name_buffer_->AppendBytes(kLogEventsNames[tag]);
864 name_buffer_->AppendByte(':');
865 name_buffer_->AppendBytes(comment);
866 }
867 if (FLAG_ll_prof) {
868 LowLevelCodeCreateEvent(code, name_buffer_->get(), name_buffer_->size());
869 }
870 if (Serializer::enabled()) {
871 RegisterSnapshotCodeName(code, name_buffer_->get(), name_buffer_->size());
872 }
873 if (!FLAG_log_code) return;
739 LogMessageBuilder msg(this); 874 LogMessageBuilder msg(this);
740 msg.Append("%s,%s,", 875 msg.Append("%s,%s,",
741 kLogEventsNames[CODE_CREATION_EVENT], 876 kLogEventsNames[CODE_CREATION_EVENT],
742 kLogEventsNames[tag]); 877 kLogEventsNames[tag]);
743 msg.AppendAddress(code->address()); 878 msg.AppendAddress(code->address());
744 msg.Append(",%d,\"", code->ExecutableSize()); 879 msg.Append(",%d,\"", code->ExecutableSize());
745 for (const char* p = comment; *p != '\0'; p++) { 880 for (const char* p = comment; *p != '\0'; p++) {
746 if (*p == '"') { 881 if (*p == '"') {
747 msg.Append('\\'); 882 msg.Append('\\');
748 } 883 }
749 msg.Append(*p); 884 msg.Append(*p);
750 } 885 }
751 msg.Append('"'); 886 msg.Append('"');
752 LowLevelCodeCreateEvent(code, &msg);
753 msg.Append('\n'); 887 msg.Append('\n');
754 msg.WriteToLogFile(); 888 msg.WriteToLogFile();
755 #endif 889 #endif
756 } 890 }
757 891
758 892
759 void Logger::CodeCreateEvent(LogEventsAndTags tag, 893 void Logger::CodeCreateEvent(LogEventsAndTags tag,
760 Code* code, 894 Code* code,
761 String* name) { 895 String* name) {
762 #ifdef ENABLE_LOGGING_AND_PROFILING 896 #ifdef ENABLE_LOGGING_AND_PROFILING
763 if (name != NULL) { 897 if (!log_->IsEnabled()) return;
764 SmartPointer<char> str = 898 if (FLAG_ll_prof || Serializer::enabled()) {
765 name->ToCString(DISALLOW_NULLS, ROBUST_STRING_TRAVERSAL); 899 name_buffer_->Reset();
766 CodeCreateEvent(tag, code, *str); 900 name_buffer_->AppendBytes(kLogEventsNames[tag]);
767 } else { 901 name_buffer_->AppendByte(':');
768 CodeCreateEvent(tag, code, ""); 902 name_buffer_->AppendString(name);
769 } 903 }
904 if (FLAG_ll_prof) {
905 LowLevelCodeCreateEvent(code, name_buffer_->get(), name_buffer_->size());
906 }
907 if (Serializer::enabled()) {
908 RegisterSnapshotCodeName(code, name_buffer_->get(), name_buffer_->size());
909 }
910 if (!FLAG_log_code) return;
911 LogMessageBuilder msg(this);
912 msg.Append("%s,%s,",
913 kLogEventsNames[CODE_CREATION_EVENT],
914 kLogEventsNames[tag]);
915 msg.AppendAddress(code->address());
916 msg.Append(",%d,\"", code->ExecutableSize());
917 msg.AppendDetailed(name, false);
918 msg.Append('"');
919 msg.Append('\n');
920 msg.WriteToLogFile();
770 #endif 921 #endif
771 } 922 }
772 923
773 924
774 #ifdef ENABLE_LOGGING_AND_PROFILING 925 #ifdef ENABLE_LOGGING_AND_PROFILING
775 // ComputeMarker must only be used when SharedFunctionInfo is known. 926 // ComputeMarker must only be used when SharedFunctionInfo is known.
776 static const char* ComputeMarker(Code* code) { 927 static const char* ComputeMarker(Code* code) {
777 switch (code->kind()) { 928 switch (code->kind()) {
778 case Code::FUNCTION: return code->optimizable() ? "~" : ""; 929 case Code::FUNCTION: return code->optimizable() ? "~" : "";
779 case Code::OPTIMIZED_FUNCTION: return "*"; 930 case Code::OPTIMIZED_FUNCTION: return "*";
780 default: return ""; 931 default: return "";
781 } 932 }
782 } 933 }
783 #endif 934 #endif
784 935
785 936
786 void Logger::CodeCreateEvent(LogEventsAndTags tag, 937 void Logger::CodeCreateEvent(LogEventsAndTags tag,
787 Code* code, 938 Code* code,
788 SharedFunctionInfo* shared, 939 SharedFunctionInfo* shared,
789 String* name) { 940 String* name) {
790 #ifdef ENABLE_LOGGING_AND_PROFILING 941 #ifdef ENABLE_LOGGING_AND_PROFILING
791 if (!log_->IsEnabled() || !FLAG_log_code) return; 942 if (!log_->IsEnabled()) return;
943 if (FLAG_ll_prof || Serializer::enabled()) {
944 name_buffer_->Reset();
945 name_buffer_->AppendBytes(kLogEventsNames[tag]);
946 name_buffer_->AppendByte(':');
947 name_buffer_->AppendString(name);
948 }
949 if (FLAG_ll_prof) {
950 LowLevelCodeCreateEvent(code, name_buffer_->get(), name_buffer_->size());
951 }
952 if (Serializer::enabled()) {
953 RegisterSnapshotCodeName(code, name_buffer_->get(), name_buffer_->size());
954 }
955 if (!FLAG_log_code) return;
792 if (code == Isolate::Current()->builtins()->builtin( 956 if (code == Isolate::Current()->builtins()->builtin(
793 Builtins::kLazyCompile)) 957 Builtins::kLazyCompile))
794 return; 958 return;
795 959
796 LogMessageBuilder msg(this); 960 LogMessageBuilder msg(this);
797 SmartPointer<char> str = 961 SmartPointer<char> str =
798 name->ToCString(DISALLOW_NULLS, ROBUST_STRING_TRAVERSAL); 962 name->ToCString(DISALLOW_NULLS, ROBUST_STRING_TRAVERSAL);
799 msg.Append("%s,%s,", 963 msg.Append("%s,%s,",
800 kLogEventsNames[CODE_CREATION_EVENT], 964 kLogEventsNames[CODE_CREATION_EVENT],
801 kLogEventsNames[tag]); 965 kLogEventsNames[tag]);
802 msg.AppendAddress(code->address()); 966 msg.AppendAddress(code->address());
803 msg.Append(",%d,\"%s\",", code->ExecutableSize(), *str); 967 msg.Append(",%d,\"%s\",", code->ExecutableSize(), *str);
804 msg.AppendAddress(shared->address()); 968 msg.AppendAddress(shared->address());
805 msg.Append(",%s", ComputeMarker(code)); 969 msg.Append(",%s", ComputeMarker(code));
806 LowLevelCodeCreateEvent(code, &msg);
807 msg.Append('\n'); 970 msg.Append('\n');
808 msg.WriteToLogFile(); 971 msg.WriteToLogFile();
809 #endif 972 #endif
810 } 973 }
811 974
812 975
813 // Although, it is possible to extract source and line from 976 // Although, it is possible to extract source and line from
814 // the SharedFunctionInfo object, we left it to caller 977 // the SharedFunctionInfo object, we left it to caller
815 // to leave logging functions free from heap allocations. 978 // to leave logging functions free from heap allocations.
816 void Logger::CodeCreateEvent(LogEventsAndTags tag, 979 void Logger::CodeCreateEvent(LogEventsAndTags tag,
817 Code* code, 980 Code* code,
818 SharedFunctionInfo* shared, 981 SharedFunctionInfo* shared,
819 String* source, int line) { 982 String* source, int line) {
820 #ifdef ENABLE_LOGGING_AND_PROFILING 983 #ifdef ENABLE_LOGGING_AND_PROFILING
821 if (!log_->IsEnabled() || !FLAG_log_code) return; 984 if (!log_->IsEnabled()) return;
985 if (FLAG_ll_prof || Serializer::enabled()) {
986 name_buffer_->Reset();
987 name_buffer_->AppendBytes(kLogEventsNames[tag]);
988 name_buffer_->AppendByte(':');
989 name_buffer_->AppendString(shared->DebugName());
990 name_buffer_->AppendByte(' ');
991 name_buffer_->AppendString(source);
992 name_buffer_->AppendByte(':');
993 name_buffer_->AppendInt(line);
994 }
995 if (FLAG_ll_prof) {
996 LowLevelCodeCreateEvent(code, name_buffer_->get(), name_buffer_->size());
997 }
998 if (Serializer::enabled()) {
999 RegisterSnapshotCodeName(code, name_buffer_->get(), name_buffer_->size());
1000 }
1001 if (!FLAG_log_code) return;
822 LogMessageBuilder msg(this); 1002 LogMessageBuilder msg(this);
823 SmartPointer<char> name = 1003 SmartPointer<char> name =
824 shared->DebugName()->ToCString(DISALLOW_NULLS, ROBUST_STRING_TRAVERSAL); 1004 shared->DebugName()->ToCString(DISALLOW_NULLS, ROBUST_STRING_TRAVERSAL);
825 SmartPointer<char> sourcestr = 1005 SmartPointer<char> sourcestr =
826 source->ToCString(DISALLOW_NULLS, ROBUST_STRING_TRAVERSAL); 1006 source->ToCString(DISALLOW_NULLS, ROBUST_STRING_TRAVERSAL);
827 msg.Append("%s,%s,", 1007 msg.Append("%s,%s,",
828 kLogEventsNames[CODE_CREATION_EVENT], 1008 kLogEventsNames[CODE_CREATION_EVENT],
829 kLogEventsNames[tag]); 1009 kLogEventsNames[tag]);
830 msg.AppendAddress(code->address()); 1010 msg.AppendAddress(code->address());
831 msg.Append(",%d,\"%s %s:%d\",", 1011 msg.Append(",%d,\"%s %s:%d\",",
832 code->ExecutableSize(), 1012 code->ExecutableSize(),
833 *name, 1013 *name,
834 *sourcestr, 1014 *sourcestr,
835 line); 1015 line);
836 msg.AppendAddress(shared->address()); 1016 msg.AppendAddress(shared->address());
837 msg.Append(",%s", ComputeMarker(code)); 1017 msg.Append(",%s", ComputeMarker(code));
838 LowLevelCodeCreateEvent(code, &msg);
839 msg.Append('\n'); 1018 msg.Append('\n');
840 msg.WriteToLogFile(); 1019 msg.WriteToLogFile();
841 #endif 1020 #endif
842 } 1021 }
843 1022
844 1023
845 void Logger::CodeCreateEvent(LogEventsAndTags tag, Code* code, int args_count) { 1024 void Logger::CodeCreateEvent(LogEventsAndTags tag, Code* code, int args_count) {
846 #ifdef ENABLE_LOGGING_AND_PROFILING 1025 #ifdef ENABLE_LOGGING_AND_PROFILING
847 if (!log_->IsEnabled() || !FLAG_log_code) return; 1026 if (!log_->IsEnabled()) return;
1027 if (FLAG_ll_prof || Serializer::enabled()) {
1028 name_buffer_->Reset();
1029 name_buffer_->AppendBytes(kLogEventsNames[tag]);
1030 name_buffer_->AppendByte(':');
1031 name_buffer_->AppendInt(args_count);
1032 }
1033 if (FLAG_ll_prof) {
1034 LowLevelCodeCreateEvent(code, name_buffer_->get(), name_buffer_->size());
1035 }
1036 if (Serializer::enabled()) {
1037 RegisterSnapshotCodeName(code, name_buffer_->get(), name_buffer_->size());
1038 }
1039 if (!FLAG_log_code) return;
848 LogMessageBuilder msg(this); 1040 LogMessageBuilder msg(this);
849 msg.Append("%s,%s,", 1041 msg.Append("%s,%s,",
850 kLogEventsNames[CODE_CREATION_EVENT], 1042 kLogEventsNames[CODE_CREATION_EVENT],
851 kLogEventsNames[tag]); 1043 kLogEventsNames[tag]);
852 msg.AppendAddress(code->address()); 1044 msg.AppendAddress(code->address());
853 msg.Append(",%d,\"args_count: %d\"", code->ExecutableSize(), args_count); 1045 msg.Append(",%d,\"args_count: %d\"", code->ExecutableSize(), args_count);
854 LowLevelCodeCreateEvent(code, &msg);
855 msg.Append('\n'); 1046 msg.Append('\n');
856 msg.WriteToLogFile(); 1047 msg.WriteToLogFile();
857 #endif 1048 #endif
858 } 1049 }
859 1050
860 1051
861 void Logger::CodeMovingGCEvent() { 1052 void Logger::CodeMovingGCEvent() {
862 #ifdef ENABLE_LOGGING_AND_PROFILING 1053 #ifdef ENABLE_LOGGING_AND_PROFILING
863 if (!log_->IsEnabled() || !FLAG_log_code || !FLAG_ll_prof) return; 1054 if (!log_->IsEnabled() || !FLAG_ll_prof) return;
864 LogMessageBuilder msg(this); 1055 LowLevelLogWriteBytes(&kCodeMovingGCTag, sizeof(kCodeMovingGCTag));
865 msg.Append("%s\n", kLogEventsNames[CODE_MOVING_GC]);
866 msg.WriteToLogFile();
867 OS::SignalCodeMovingGC(); 1056 OS::SignalCodeMovingGC();
868 #endif 1057 #endif
869 } 1058 }
870 1059
871 1060
872 void Logger::RegExpCodeCreateEvent(Code* code, String* source) { 1061 void Logger::RegExpCodeCreateEvent(Code* code, String* source) {
873 #ifdef ENABLE_LOGGING_AND_PROFILING 1062 #ifdef ENABLE_LOGGING_AND_PROFILING
874 if (!log_->IsEnabled() || !FLAG_log_code) return; 1063 if (!log_->IsEnabled()) return;
1064 if (FLAG_ll_prof || Serializer::enabled()) {
1065 name_buffer_->Reset();
1066 name_buffer_->AppendBytes(kLogEventsNames[REG_EXP_TAG]);
1067 name_buffer_->AppendByte(':');
1068 name_buffer_->AppendString(source);
1069 }
1070 if (FLAG_ll_prof) {
1071 LowLevelCodeCreateEvent(code, name_buffer_->get(), name_buffer_->size());
1072 }
1073 if (Serializer::enabled()) {
1074 RegisterSnapshotCodeName(code, name_buffer_->get(), name_buffer_->size());
1075 }
1076 if (!FLAG_log_code) return;
875 LogMessageBuilder msg(this); 1077 LogMessageBuilder msg(this);
876 msg.Append("%s,%s,", 1078 msg.Append("%s,%s,",
877 kLogEventsNames[CODE_CREATION_EVENT], 1079 kLogEventsNames[CODE_CREATION_EVENT],
878 kLogEventsNames[REG_EXP_TAG]); 1080 kLogEventsNames[REG_EXP_TAG]);
879 msg.AppendAddress(code->address()); 1081 msg.AppendAddress(code->address());
880 msg.Append(",%d,\"", code->ExecutableSize()); 1082 msg.Append(",%d,\"", code->ExecutableSize());
881 msg.AppendDetailed(source, false); 1083 msg.AppendDetailed(source, false);
882 msg.Append('\"'); 1084 msg.Append('\"');
883 LowLevelCodeCreateEvent(code, &msg);
884 msg.Append('\n'); 1085 msg.Append('\n');
885 msg.WriteToLogFile(); 1086 msg.WriteToLogFile();
886 #endif 1087 #endif
887 } 1088 }
888 1089
889 1090
890 void Logger::CodeMoveEvent(Address from, Address to) { 1091 void Logger::CodeMoveEvent(Address from, Address to) {
891 #ifdef ENABLE_LOGGING_AND_PROFILING 1092 #ifdef ENABLE_LOGGING_AND_PROFILING
1093 if (!log_->IsEnabled()) return;
1094 if (FLAG_ll_prof) LowLevelCodeMoveEvent(from, to);
1095 if (Serializer::enabled() && address_to_name_map_ != NULL) {
1096 Address code_address = from + Code::kHeaderSize;
1097 uint32_t hash = ComputePointerHash(code_address);
1098 HashMap::Entry* entry = address_to_name_map_->Lookup(
mnaganov (inactive) 2011/04/29 14:20:28 This code is repeated several times. Worth extract
Vitaly Repeshko 2011/04/29 15:50:40 Created a class. It's +20 lines overall, but the c
1099 code_address, hash, false);
1100 ASSERT(entry != NULL);
1101 void* value = entry->value;
1102 address_to_name_map_->Remove(code_address, hash);
1103 entry = address_to_name_map_->Lookup(code_address, hash, true);
1104 ASSERT(entry->value == NULL);
1105 entry->value = value;
1106 return;
1107 }
892 MoveEventInternal(CODE_MOVE_EVENT, from, to); 1108 MoveEventInternal(CODE_MOVE_EVENT, from, to);
893 #endif 1109 #endif
894 } 1110 }
895 1111
896 1112
897 void Logger::CodeDeleteEvent(Address from) { 1113 void Logger::CodeDeleteEvent(Address from) {
898 #ifdef ENABLE_LOGGING_AND_PROFILING 1114 #ifdef ENABLE_LOGGING_AND_PROFILING
1115 if (!log_->IsEnabled()) return;
1116 if (FLAG_ll_prof) LowLevelCodeDeleteEvent(from);
1117 if (Serializer::enabled() && address_to_name_map_ != NULL) {
1118 Address code_address = from + Code::kHeaderSize;
1119 uint32_t hash = ComputePointerHash(code_address);
1120 HashMap::Entry* entry = address_to_name_map_->Lookup(
1121 code_address, hash, false);
1122 if (entry != NULL) {
1123 DeleteArray(static_cast<const char*>(entry->value));
1124 }
1125 address_to_name_map_->Remove(code_address, hash);
1126 return;
1127 }
899 DeleteEventInternal(CODE_DELETE_EVENT, from); 1128 DeleteEventInternal(CODE_DELETE_EVENT, from);
900 #endif 1129 #endif
901 } 1130 }
902 1131
903 1132
904 void Logger::SnapshotPositionEvent(Address addr, int pos) { 1133 void Logger::SnapshotPositionEvent(Address addr, int pos) {
905 #ifdef ENABLE_LOGGING_AND_PROFILING 1134 #ifdef ENABLE_LOGGING_AND_PROFILING
906 if (!log_->IsEnabled() || !FLAG_log_snapshot_positions) return; 1135 if (!log_->IsEnabled()) return;
1136 if (FLAG_ll_prof) LowLevelSnapshotPositionEvent(addr, pos);
1137 if (Serializer::enabled() && address_to_name_map_ != NULL) {
1138 Address code_address = addr + Code::kHeaderSize;
1139 HashMap::Entry* entry = address_to_name_map_->Lookup(
1140 code_address, ComputePointerHash(code_address), false);
1141 if (entry == NULL) return; // Not a code object.
1142 LogMessageBuilder msg(this);
1143 msg.Append("%s,%d,\"", kLogEventsNames[SNAPSHOT_CODE_NAME_EVENT], pos);
1144 for (const char* p = static_cast<const char*>(entry->value);
1145 *p != '\0';
1146 ++p) {
1147 if (*p == '"') msg.Append('\\');
1148 msg.Append(*p);
1149 }
1150 msg.Append("\"\n");
1151 msg.WriteToLogFile();
1152 }
1153 if (!FLAG_log_snapshot_positions) return;
907 LogMessageBuilder msg(this); 1154 LogMessageBuilder msg(this);
908 msg.Append("%s,", kLogEventsNames[SNAPSHOT_POSITION_EVENT]); 1155 msg.Append("%s,", kLogEventsNames[SNAPSHOT_POSITION_EVENT]);
909 msg.AppendAddress(addr); 1156 msg.AppendAddress(addr);
910 msg.Append(",%d", pos); 1157 msg.Append(",%d", pos);
911 msg.Append('\n'); 1158 msg.Append('\n');
912 msg.WriteToLogFile(); 1159 msg.WriteToLogFile();
913 #endif 1160 #endif
914 } 1161 }
915 1162
916 1163
(...skipping 384 matching lines...) Expand 10 before | Expand all | Expand 10 after
1301 EnumerateOptimizedFunctionsVisitor visitor(sfis, 1548 EnumerateOptimizedFunctionsVisitor visitor(sfis,
1302 code_objects, 1549 code_objects,
1303 &compiled_funcs_count); 1550 &compiled_funcs_count);
1304 Deoptimizer::VisitAllOptimizedFunctions(&visitor); 1551 Deoptimizer::VisitAllOptimizedFunctions(&visitor);
1305 1552
1306 return compiled_funcs_count; 1553 return compiled_funcs_count;
1307 } 1554 }
1308 1555
1309 1556
1310 void Logger::LogCodeObject(Object* object) { 1557 void Logger::LogCodeObject(Object* object) {
1311 if (FLAG_log_code) { 1558 if (FLAG_log_code || FLAG_ll_prof) {
1312 Code* code_object = Code::cast(object); 1559 Code* code_object = Code::cast(object);
1313 LogEventsAndTags tag = Logger::STUB_TAG; 1560 LogEventsAndTags tag = Logger::STUB_TAG;
1314 const char* description = "Unknown code from the snapshot"; 1561 const char* description = "Unknown code from the snapshot";
1315 switch (code_object->kind()) { 1562 switch (code_object->kind()) {
1316 case Code::FUNCTION: 1563 case Code::FUNCTION:
1317 case Code::OPTIMIZED_FUNCTION: 1564 case Code::OPTIMIZED_FUNCTION:
1318 return; // We log this later using LogCompiledFunctions. 1565 return; // We log this later using LogCompiledFunctions.
1319 case Code::TYPE_RECORDING_BINARY_OP_IC: // fall through 1566 case Code::TYPE_RECORDING_BINARY_OP_IC: // fall through
1320 case Code::COMPARE_IC: // fall through 1567 case Code::COMPARE_IC: // fall through
1321 case Code::STUB: 1568 case Code::STUB:
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
1362 tag = Logger::KEYED_CALL_IC_TAG; 1609 tag = Logger::KEYED_CALL_IC_TAG;
1363 break; 1610 break;
1364 } 1611 }
1365 PROFILE(ISOLATE, CodeCreateEvent(tag, code_object, description)); 1612 PROFILE(ISOLATE, CodeCreateEvent(tag, code_object, description));
1366 } 1613 }
1367 } 1614 }
1368 1615
1369 1616
1370 void Logger::LogCodeInfo() { 1617 void Logger::LogCodeInfo() {
1371 #ifdef ENABLE_LOGGING_AND_PROFILING 1618 #ifdef ENABLE_LOGGING_AND_PROFILING
1372 if (!log_->IsEnabled() || !FLAG_log_code || !FLAG_ll_prof) return; 1619 if (!log_->IsEnabled() || !FLAG_ll_prof) return;
1373 #if V8_TARGET_ARCH_IA32 1620 #if V8_TARGET_ARCH_IA32
1374 const char arch[] = "ia32"; 1621 const char arch[] = "ia32";
1375 #elif V8_TARGET_ARCH_X64 1622 #elif V8_TARGET_ARCH_X64
1376 const char arch[] = "x64"; 1623 const char arch[] = "x64";
1377 #elif V8_TARGET_ARCH_ARM 1624 #elif V8_TARGET_ARCH_ARM
1378 const char arch[] = "arm"; 1625 const char arch[] = "arm";
1379 #else 1626 #else
1380 const char arch[] = "unknown"; 1627 const char arch[] = "unknown";
1381 #endif 1628 #endif
1382 LogMessageBuilder msg(this); 1629 LowLevelLogWriteBytes(arch, sizeof(arch));
1383 msg.Append("code-info,%s,%d\n", arch, Code::kHeaderSize);
1384 msg.WriteToLogFile();
1385 #endif // ENABLE_LOGGING_AND_PROFILING 1630 #endif // ENABLE_LOGGING_AND_PROFILING
1386 } 1631 }
1387 1632
1388 1633
1389 void Logger::LowLevelCodeCreateEvent(Code* code, LogMessageBuilder* msg) { 1634 static char* CopyName(const char* name, int name_size) {
1390 if (!FLAG_ll_prof || log_->output_code_handle_ == NULL) return; 1635 char* result = NewArray<char>(name_size + 1);
1391 int pos = static_cast<int>(ftell(log_->output_code_handle_)); 1636 for (int i = 0; i < name_size; ++i) {
1392 size_t rv = fwrite(code->instruction_start(), 1, code->instruction_size(), 1637 char c = name[i];
1393 log_->output_code_handle_); 1638 if (c == '\0') c = ' ';
1394 ASSERT(static_cast<size_t>(code->instruction_size()) == rv); 1639 result[i] = c;
1395 USE(rv); 1640 }
1396 msg->Append(",%d", pos); 1641 result[name_size] = '\0';
1642 return result;
1397 } 1643 }
1398 1644
1399 1645
1646 void Logger::RegisterSnapshotCodeName(Code* code,
1647 const char* name,
1648 int name_size) {
1649 ASSERT(Serializer::enabled());
1650 if (address_to_name_map_ == NULL) {
1651 address_to_name_map_ = new HashMap(&PointerEquals);
1652 }
1653 Address code_address = code->instruction_start();
1654 HashMap::Entry* entry = address_to_name_map_->Lookup(
1655 code_address, ComputePointerHash(code_address), true);
1656 if (entry->value == NULL) {
1657 entry->value = CopyName(name, name_size);
1658 }
1659 }
1660
1661
1662 void Logger::LowLevelCodeCreateEvent(Code* code,
1663 const char* name,
1664 int name_size) {
1665 if (log_->ll_output_handle_ == NULL) return;
1666 LowLevelCodeCreateStruct event;
1667 event.name_size = name_size;
1668 event.code_address = code->instruction_start();
1669 ASSERT(event.code_address == code->address() + Code::kHeaderSize);
1670 event.code_size = code->instruction_size();
1671 LowLevelLogWriteStruct(event);
1672 LowLevelLogWriteBytes(name, name_size);
1673 LowLevelLogWriteBytes(
1674 reinterpret_cast<const char*>(code->instruction_start()),
1675 code->instruction_size());
1676 }
1677
1678
1679 void Logger::LowLevelCodeMoveEvent(Address from, Address to) {
1680 if (log_->ll_output_handle_ == NULL) return;
1681 LowLevelCodeMoveStruct event;
1682 event.from_address = from + Code::kHeaderSize;
1683 event.to_address = to + Code::kHeaderSize;
1684 LowLevelLogWriteStruct(event);
1685 }
1686
1687
1688 void Logger::LowLevelCodeDeleteEvent(Address from) {
1689 if (log_->ll_output_handle_ == NULL) return;
1690 LowLevelCodeDeleteStruct event;
1691 event.address = from + Code::kHeaderSize;
1692 LowLevelLogWriteStruct(event);
1693 }
1694
1695
1696 void Logger::LowLevelSnapshotPositionEvent(Address addr, int pos) {
1697 if (log_->ll_output_handle_ == NULL) return;
1698 LowLevelSnapshotPositionStruct event;
1699 event.address = addr + Code::kHeaderSize;
1700 event.position = pos;
1701 LowLevelLogWriteStruct(event);
1702 }
1703
1704
1705 void Logger::LowLevelLogWriteBytes(const char* bytes, int size) {
1706 size_t rv = fwrite(bytes, 1, size, log_->ll_output_handle_);
1707 ASSERT(static_cast<size_t>(size) == rv);
1708 USE(rv);
1709 }
1710
1711
1400 void Logger::LogCodeObjects() { 1712 void Logger::LogCodeObjects() {
1401 AssertNoAllocation no_alloc; 1713 AssertNoAllocation no_alloc;
1402 HeapIterator iterator; 1714 HeapIterator iterator;
1403 for (HeapObject* obj = iterator.next(); obj != NULL; obj = iterator.next()) { 1715 for (HeapObject* obj = iterator.next(); obj != NULL; obj = iterator.next()) {
1404 if (obj->IsCode()) LogCodeObject(obj); 1716 if (obj->IsCode()) LogCodeObject(obj);
1405 } 1717 }
1406 } 1718 }
1407 1719
1408 1720
1409 void Logger::LogCompiledFunctions() { 1721 void Logger::LogCompiledFunctions() {
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after
1489 1801
1490 1802
1491 bool Logger::Setup() { 1803 bool Logger::Setup() {
1492 #ifdef ENABLE_LOGGING_AND_PROFILING 1804 #ifdef ENABLE_LOGGING_AND_PROFILING
1493 // Tests and EnsureInitialize() can call this twice in a row. It's harmless. 1805 // Tests and EnsureInitialize() can call this twice in a row. It's harmless.
1494 if (is_initialized_) return true; 1806 if (is_initialized_) return true;
1495 is_initialized_ = true; 1807 is_initialized_ = true;
1496 1808
1497 // --ll-prof implies --log-code and --log-snapshot-positions. 1809 // --ll-prof implies --log-code and --log-snapshot-positions.
1498 if (FLAG_ll_prof) { 1810 if (FLAG_ll_prof) {
1499 FLAG_log_code = true;
1500 FLAG_log_snapshot_positions = true; 1811 FLAG_log_snapshot_positions = true;
1501 } 1812 }
1502 1813
1503 // --prof_lazy controls --log-code, implies --noprof_auto. 1814 // --prof_lazy controls --log-code, implies --noprof_auto.
1504 if (FLAG_prof_lazy) { 1815 if (FLAG_prof_lazy) {
1505 FLAG_log_code = false; 1816 FLAG_log_code = false;
1506 FLAG_prof_auto = false; 1817 FLAG_prof_auto = false;
1507 } 1818 }
1508 1819
1509 // TODO(isolates): this assert introduces cyclic dependency (logger 1820 // TODO(isolates): this assert introduces cyclic dependency (logger
1510 // -> thread local top -> heap -> logger). 1821 // -> thread local top -> heap -> logger).
1511 // ASSERT(VMState::is_outermost_external()); 1822 // ASSERT(VMState::is_outermost_external());
1512 1823
1513 log_->Initialize(); 1824 log_->Initialize();
1514 1825
1515 if (FLAG_ll_prof) LogCodeInfo(); 1826 if (FLAG_ll_prof) LogCodeInfo();
1516 1827
1517 ticker_ = new Ticker(Isolate::Current(), kSamplingIntervalMs); 1828 ticker_ = new Ticker(Isolate::Current(), kSamplingIntervalMs);
1518 1829
1519 Isolate* isolate = Isolate::Current(); 1830 Isolate* isolate = Isolate::Current();
1520 if (FLAG_sliding_state_window && sliding_state_window_ == NULL) { 1831 if (FLAG_sliding_state_window && sliding_state_window_ == NULL) {
1521 sliding_state_window_ = new SlidingStateWindow(isolate); 1832 sliding_state_window_ = new SlidingStateWindow(isolate);
1522 } 1833 }
1523 1834
1524 bool start_logging = FLAG_log || FLAG_log_runtime || FLAG_log_api 1835 bool start_logging = FLAG_log || FLAG_log_runtime || FLAG_log_api
1525 || FLAG_log_code || FLAG_log_gc || FLAG_log_handles || FLAG_log_suspect 1836 || FLAG_log_code || FLAG_log_gc || FLAG_log_handles || FLAG_log_suspect
1526 || FLAG_log_regexp || FLAG_log_state_changes; 1837 || FLAG_log_regexp || FLAG_log_state_changes || FLAG_ll_prof;
1527 1838
1528 if (start_logging) { 1839 if (start_logging) {
1529 logging_nesting_ = 1; 1840 logging_nesting_ = 1;
1530 } 1841 }
1531 1842
1532 if (FLAG_prof) { 1843 if (FLAG_prof) {
1533 profiler_ = new Profiler(isolate); 1844 profiler_ = new Profiler(isolate);
1534 if (!FLAG_prof_auto) { 1845 if (!FLAG_prof_auto) {
1535 profiler_->pause(); 1846 profiler_->pause();
1536 } else { 1847 } else {
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after
1656 void SamplerRegistry::RemoveActiveSampler(Sampler* sampler) { 1967 void SamplerRegistry::RemoveActiveSampler(Sampler* sampler) {
1657 ASSERT(sampler->IsActive()); 1968 ASSERT(sampler->IsActive());
1658 ScopedLock lock(mutex_); 1969 ScopedLock lock(mutex_);
1659 ASSERT(active_samplers_ != NULL); 1970 ASSERT(active_samplers_ != NULL);
1660 bool removed = active_samplers_->RemoveElement(sampler); 1971 bool removed = active_samplers_->RemoveElement(sampler);
1661 ASSERT(removed); 1972 ASSERT(removed);
1662 USE(removed); 1973 USE(removed);
1663 } 1974 }
1664 1975
1665 } } // namespace v8::internal 1976 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/log.h ('k') | src/log-utils.h » ('j') | src/utils.h » ('J')

Powered by Google App Engine
This is Rietveld 408576698