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

Side by Side Diff: src/frames.cc

Issue 1907443002: Introduce approximate mode for StandardFrame::Summarize. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Addressed review feedback Created 4 years, 8 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/frames.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 #include "src/frames.h" 5 #include "src/frames.h"
6 6
7 #include <sstream> 7 #include <sstream>
8 8
9 #include "src/ast/ast.h" 9 #include "src/ast/ast.h"
10 #include "src/ast/scopeinfo.h" 10 #include "src/ast/scopeinfo.h"
(...skipping 599 matching lines...) Expand 10 before | Expand all | Expand 10 after
610 state->fp = fp; 610 state->fp = fp;
611 state->pc_address = ResolveReturnAddressLocation( 611 state->pc_address = ResolveReturnAddressLocation(
612 reinterpret_cast<Address*>(sp - 1 * kPCOnStackSize)); 612 reinterpret_cast<Address*>(sp - 1 * kPCOnStackSize));
613 // The constant pool recorded in the exit frame is not associated 613 // The constant pool recorded in the exit frame is not associated
614 // with the pc in this state (the return address into a C entry 614 // with the pc in this state (the return address into a C entry
615 // stub). ComputeCallerState will retrieve the constant pool 615 // stub). ComputeCallerState will retrieve the constant pool
616 // together with the associated caller pc. 616 // together with the associated caller pc.
617 state->constant_pool_address = NULL; 617 state->constant_pool_address = NULL;
618 } 618 }
619 619
620 void StandardFrame::Summarize(List<FrameSummary>* functions) const { 620 void StandardFrame::Summarize(List<FrameSummary>* functions,
621 FrameSummary::Mode mode) const {
621 DCHECK(functions->length() == 0); 622 DCHECK(functions->length() == 0);
622 // default implementation: no summary added 623 // default implementation: no summary added
623 } 624 }
624 625
625 JSFunction* StandardFrame::function() const { 626 JSFunction* StandardFrame::function() const {
626 // this default implementation is overridden by JS and WASM frames 627 // this default implementation is overridden by JS and WASM frames
627 return nullptr; 628 return nullptr;
628 } 629 }
629 630
630 Object* StandardFrame::receiver() const { 631 Object* StandardFrame::receiver() const {
(...skipping 222 matching lines...) Expand 10 before | Expand all | Expand 10 after
853 Address JavaScriptFrame::GetCallerStackPointer() const { 854 Address JavaScriptFrame::GetCallerStackPointer() const {
854 return fp() + StandardFrameConstants::kCallerSPOffset; 855 return fp() + StandardFrameConstants::kCallerSPOffset;
855 } 856 }
856 857
857 858
858 void JavaScriptFrame::GetFunctions(List<JSFunction*>* functions) const { 859 void JavaScriptFrame::GetFunctions(List<JSFunction*>* functions) const {
859 DCHECK(functions->length() == 0); 860 DCHECK(functions->length() == 0);
860 functions->Add(function()); 861 functions->Add(function());
861 } 862 }
862 863
863 void JavaScriptFrame::Summarize(List<FrameSummary>* functions) const { 864 void JavaScriptFrame::Summarize(List<FrameSummary>* functions,
865 FrameSummary::Mode mode) const {
864 DCHECK(functions->length() == 0); 866 DCHECK(functions->length() == 0);
865 Code* code = LookupCode(); 867 Code* code = LookupCode();
866 int offset = static_cast<int>(pc() - code->instruction_start()); 868 int offset = static_cast<int>(pc() - code->instruction_start());
867 AbstractCode* abstract_code = AbstractCode::cast(code); 869 AbstractCode* abstract_code = AbstractCode::cast(code);
868 FrameSummary summary(receiver(), function(), abstract_code, offset, 870 FrameSummary summary(receiver(), function(), abstract_code, offset,
869 IsConstructor()); 871 IsConstructor(), mode);
870 functions->Add(summary); 872 functions->Add(summary);
871 } 873 }
872 874
873 JSFunction* JavaScriptFrame::function() const { 875 JSFunction* JavaScriptFrame::function() const {
874 return JSFunction::cast(function_slot_object()); 876 return JSFunction::cast(function_slot_object());
875 } 877 }
876 878
877 Object* JavaScriptFrame::receiver() const { return GetParameter(-1); } 879 Object* JavaScriptFrame::receiver() const { return GetParameter(-1); }
878 880
879 int JavaScriptFrame::LookupExceptionHandlerInTable( 881 int JavaScriptFrame::LookupExceptionHandlerInTable(
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after
959 961
960 bool CannotDeoptFromAsmCode(Code* code, JSFunction* function) { 962 bool CannotDeoptFromAsmCode(Code* code, JSFunction* function) {
961 return code->is_turbofanned() && function->shared()->asm_function() && 963 return code->is_turbofanned() && function->shared()->asm_function() &&
962 !FLAG_turbo_asm_deoptimization; 964 !FLAG_turbo_asm_deoptimization;
963 } 965 }
964 966
965 } // namespace 967 } // namespace
966 968
967 FrameSummary::FrameSummary(Object* receiver, JSFunction* function, 969 FrameSummary::FrameSummary(Object* receiver, JSFunction* function,
968 AbstractCode* abstract_code, int code_offset, 970 AbstractCode* abstract_code, int code_offset,
969 bool is_constructor) 971 bool is_constructor, Mode mode)
970 : receiver_(receiver, function->GetIsolate()), 972 : receiver_(receiver, function->GetIsolate()),
971 function_(function), 973 function_(function),
972 abstract_code_(abstract_code), 974 abstract_code_(abstract_code),
973 code_offset_(code_offset), 975 code_offset_(code_offset),
974 is_constructor_(is_constructor) { 976 is_constructor_(is_constructor) {
975 DCHECK(abstract_code->IsBytecodeArray() || 977 DCHECK(abstract_code->IsBytecodeArray() ||
976 Code::cast(abstract_code)->kind() != Code::OPTIMIZED_FUNCTION || 978 Code::cast(abstract_code)->kind() != Code::OPTIMIZED_FUNCTION ||
977 CannotDeoptFromAsmCode(Code::cast(abstract_code), function)); 979 CannotDeoptFromAsmCode(Code::cast(abstract_code), function) ||
980 mode == kApproximateSummary);
978 } 981 }
979 982
980 FrameSummary FrameSummary::GetFirst(JavaScriptFrame* frame) { 983 FrameSummary FrameSummary::GetFirst(JavaScriptFrame* frame) {
981 List<FrameSummary> frames(FLAG_max_inlining_levels + 1); 984 List<FrameSummary> frames(FLAG_max_inlining_levels + 1);
982 frame->Summarize(&frames); 985 frame->Summarize(&frames);
983 return frames.first(); 986 return frames.first();
984 } 987 }
985 988
986 void FrameSummary::Print() { 989 void FrameSummary::Print() {
987 PrintF("receiver: "); 990 PrintF("receiver: ");
988 receiver_->ShortPrint(); 991 receiver_->ShortPrint();
989 PrintF("\nfunction: "); 992 PrintF("\nfunction: ");
990 function_->shared()->DebugName()->ShortPrint(); 993 function_->shared()->DebugName()->ShortPrint();
991 PrintF("\ncode: "); 994 PrintF("\ncode: ");
992 abstract_code_->ShortPrint(); 995 abstract_code_->ShortPrint();
993 if (abstract_code_->IsCode()) { 996 if (abstract_code_->IsCode()) {
994 Code* code = abstract_code_->GetCode(); 997 Code* code = abstract_code_->GetCode();
995 if (code->kind() == Code::FUNCTION) PrintF(" UNOPT "); 998 if (code->kind() == Code::FUNCTION) PrintF(" UNOPT ");
996 if (code->kind() == Code::OPTIMIZED_FUNCTION) { 999 if (code->kind() == Code::OPTIMIZED_FUNCTION) {
997 DCHECK(CannotDeoptFromAsmCode(code, *function())); 1000 if (function()->shared()->asm_function()) {
998 PrintF(" ASM "); 1001 DCHECK(CannotDeoptFromAsmCode(code, *function()));
1002 PrintF(" ASM ");
1003 } else {
1004 PrintF(" OPT (approximate)");
1005 }
999 } 1006 }
1000 } else { 1007 } else {
1001 PrintF(" BYTECODE "); 1008 PrintF(" BYTECODE ");
1002 } 1009 }
1003 PrintF("\npc: %d\n", code_offset_); 1010 PrintF("\npc: %d\n", code_offset_);
1004 } 1011 }
1005 1012
1006 void OptimizedFrame::Summarize(List<FrameSummary>* frames) const { 1013 void OptimizedFrame::Summarize(List<FrameSummary>* frames,
1014 FrameSummary::Mode mode) const {
1007 DCHECK(frames->length() == 0); 1015 DCHECK(frames->length() == 0);
1008 DCHECK(is_optimized()); 1016 DCHECK(is_optimized());
1009 1017
1010 // Delegate to JS frame in absence of turbofan deoptimization. 1018 // Delegate to JS frame in absence of turbofan deoptimization.
1011 // TODO(turbofan): Revisit once we support deoptimization across the board. 1019 // TODO(turbofan): Revisit once we support deoptimization across the board.
1012 Code* code = LookupCode(); 1020 Code* code = LookupCode();
1013 if (code->kind() == Code::BUILTIN || 1021 if (code->kind() == Code::BUILTIN ||
1014 CannotDeoptFromAsmCode(code, function())) { 1022 CannotDeoptFromAsmCode(code, function())) {
1015 return JavaScriptFrame::Summarize(frames); 1023 return JavaScriptFrame::Summarize(frames);
1016 } 1024 }
1017 1025
1018 DisallowHeapAllocation no_gc; 1026 DisallowHeapAllocation no_gc;
1019 int deopt_index = Safepoint::kNoDeoptimizationIndex; 1027 int deopt_index = Safepoint::kNoDeoptimizationIndex;
1020 DeoptimizationInputData* const data = GetDeoptimizationData(&deopt_index); 1028 DeoptimizationInputData* const data = GetDeoptimizationData(&deopt_index);
1029 if (deopt_index == Safepoint::kNoDeoptimizationIndex) {
1030 DCHECK(data == nullptr);
1031 if (mode == FrameSummary::kApproximateSummary) {
1032 return JavaScriptFrame::Summarize(frames, mode);
1033 }
1034 FATAL("Missing deoptimization information for OptimizedFrame::Summarize.");
1035 }
1021 FixedArray* const literal_array = data->LiteralArray(); 1036 FixedArray* const literal_array = data->LiteralArray();
1022 1037
1023 TranslationIterator it(data->TranslationByteArray(), 1038 TranslationIterator it(data->TranslationByteArray(),
1024 data->TranslationIndex(deopt_index)->value()); 1039 data->TranslationIndex(deopt_index)->value());
1025 Translation::Opcode frame_opcode = 1040 Translation::Opcode frame_opcode =
1026 static_cast<Translation::Opcode>(it.Next()); 1041 static_cast<Translation::Opcode>(it.Next());
1027 DCHECK_EQ(Translation::BEGIN, frame_opcode); 1042 DCHECK_EQ(Translation::BEGIN, frame_opcode);
1028 it.Next(); // Drop frame count. 1043 it.Next(); // Drop frame count.
1029 int jsframe_count = it.Next(); 1044 int jsframe_count = it.Next();
1030 1045
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after
1133 // code object. 1148 // code object.
1134 if (!code->contains(pc())) { 1149 if (!code->contains(pc())) {
1135 code = isolate()->inner_pointer_to_code_cache()-> 1150 code = isolate()->inner_pointer_to_code_cache()->
1136 GcSafeFindCodeForInnerPointer(pc()); 1151 GcSafeFindCodeForInnerPointer(pc());
1137 } 1152 }
1138 DCHECK(code != NULL); 1153 DCHECK(code != NULL);
1139 DCHECK(code->kind() == Code::OPTIMIZED_FUNCTION); 1154 DCHECK(code->kind() == Code::OPTIMIZED_FUNCTION);
1140 1155
1141 SafepointEntry safepoint_entry = code->GetSafepointEntry(pc()); 1156 SafepointEntry safepoint_entry = code->GetSafepointEntry(pc());
1142 *deopt_index = safepoint_entry.deoptimization_index(); 1157 *deopt_index = safepoint_entry.deoptimization_index();
1143 DCHECK(*deopt_index != Safepoint::kNoDeoptimizationIndex); 1158 if (*deopt_index != Safepoint::kNoDeoptimizationIndex) {
1144 1159 return DeoptimizationInputData::cast(code->deoptimization_data());
1145 return DeoptimizationInputData::cast(code->deoptimization_data()); 1160 }
1161 return nullptr;
1146 } 1162 }
1147 1163
1148 1164
1149 void OptimizedFrame::GetFunctions(List<JSFunction*>* functions) const { 1165 void OptimizedFrame::GetFunctions(List<JSFunction*>* functions) const {
1150 DCHECK(functions->length() == 0); 1166 DCHECK(functions->length() == 0);
1151 DCHECK(is_optimized()); 1167 DCHECK(is_optimized());
1152 1168
1153 // Delegate to JS frame in absence of turbofan deoptimization. 1169 // Delegate to JS frame in absence of turbofan deoptimization.
1154 // TODO(turbofan): Revisit once we support deoptimization across the board. 1170 // TODO(turbofan): Revisit once we support deoptimization across the board.
1155 Code* code = LookupCode(); 1171 Code* code = LookupCode();
1156 if (code->kind() == Code::BUILTIN || 1172 if (code->kind() == Code::BUILTIN ||
1157 CannotDeoptFromAsmCode(code, function())) { 1173 CannotDeoptFromAsmCode(code, function())) {
1158 return JavaScriptFrame::GetFunctions(functions); 1174 return JavaScriptFrame::GetFunctions(functions);
1159 } 1175 }
1160 1176
1161 DisallowHeapAllocation no_gc; 1177 DisallowHeapAllocation no_gc;
1162 int deopt_index = Safepoint::kNoDeoptimizationIndex; 1178 int deopt_index = Safepoint::kNoDeoptimizationIndex;
1163 DeoptimizationInputData* const data = GetDeoptimizationData(&deopt_index); 1179 DeoptimizationInputData* const data = GetDeoptimizationData(&deopt_index);
1180 DCHECK(data != nullptr && deopt_index != Safepoint::kNoDeoptimizationIndex);
1164 FixedArray* const literal_array = data->LiteralArray(); 1181 FixedArray* const literal_array = data->LiteralArray();
1165 1182
1166 TranslationIterator it(data->TranslationByteArray(), 1183 TranslationIterator it(data->TranslationByteArray(),
1167 data->TranslationIndex(deopt_index)->value()); 1184 data->TranslationIndex(deopt_index)->value());
1168 Translation::Opcode opcode = static_cast<Translation::Opcode>(it.Next()); 1185 Translation::Opcode opcode = static_cast<Translation::Opcode>(it.Next());
1169 DCHECK_EQ(Translation::BEGIN, opcode); 1186 DCHECK_EQ(Translation::BEGIN, opcode);
1170 it.Next(); // Skip frame count. 1187 it.Next(); // Skip frame count.
1171 int jsframe_count = it.Next(); 1188 int jsframe_count = it.Next();
1172 1189
1173 // We insert the frames in reverse order because the frames 1190 // We insert the frames in reverse order because the frames
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after
1260 1277
1261 void InterpretedFrame::WriteInterpreterRegister(int register_index, 1278 void InterpretedFrame::WriteInterpreterRegister(int register_index,
1262 Object* value) { 1279 Object* value) {
1263 const int index = InterpreterFrameConstants::kRegisterFileExpressionIndex; 1280 const int index = InterpreterFrameConstants::kRegisterFileExpressionIndex;
1264 DCHECK_EQ( 1281 DCHECK_EQ(
1265 InterpreterFrameConstants::kRegisterFileFromFp, 1282 InterpreterFrameConstants::kRegisterFileFromFp,
1266 InterpreterFrameConstants::kExpressionsOffset - index * kPointerSize); 1283 InterpreterFrameConstants::kExpressionsOffset - index * kPointerSize);
1267 return SetExpression(index + register_index, value); 1284 return SetExpression(index + register_index, value);
1268 } 1285 }
1269 1286
1270 void InterpretedFrame::Summarize(List<FrameSummary>* functions) const { 1287 void InterpretedFrame::Summarize(List<FrameSummary>* functions,
1288 FrameSummary::Mode mode) const {
1271 DCHECK(functions->length() == 0); 1289 DCHECK(functions->length() == 0);
1272 AbstractCode* abstract_code = 1290 AbstractCode* abstract_code =
1273 AbstractCode::cast(function()->shared()->bytecode_array()); 1291 AbstractCode::cast(function()->shared()->bytecode_array());
1274 FrameSummary summary(receiver(), function(), abstract_code, 1292 FrameSummary summary(receiver(), function(), abstract_code,
1275 GetBytecodeOffset(), IsConstructor()); 1293 GetBytecodeOffset(), IsConstructor());
1276 functions->Add(summary); 1294 functions->Add(summary);
1277 } 1295 }
1278 1296
1279 int ArgumentsAdaptorFrame::GetNumberOfIncomingArguments() const { 1297 int ArgumentsAdaptorFrame::GetNumberOfIncomingArguments() const {
1280 return Smi::cast(GetExpression(0))->value(); 1298 return Smi::cast(GetExpression(0))->value();
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
1326 1344
1327 JSFunction* WasmFrame::function() const { 1345 JSFunction* WasmFrame::function() const {
1328 // TODO(clemensh): generate the right JSFunctions once per wasm function and 1346 // TODO(clemensh): generate the right JSFunctions once per wasm function and
1329 // cache them 1347 // cache them
1330 Factory* factory = isolate()->factory(); 1348 Factory* factory = isolate()->factory();
1331 Handle<JSFunction> fun = 1349 Handle<JSFunction> fun =
1332 factory->NewFunction(factory->NewStringFromAsciiChecked("<WASM>")); 1350 factory->NewFunction(factory->NewStringFromAsciiChecked("<WASM>"));
1333 return *fun; 1351 return *fun;
1334 } 1352 }
1335 1353
1336 void WasmFrame::Summarize(List<FrameSummary>* functions) const { 1354 void WasmFrame::Summarize(List<FrameSummary>* functions,
1355 FrameSummary::Mode mode) const {
1337 DCHECK(functions->length() == 0); 1356 DCHECK(functions->length() == 0);
1338 Code* code = LookupCode(); 1357 Code* code = LookupCode();
1339 int offset = static_cast<int>(pc() - code->instruction_start()); 1358 int offset = static_cast<int>(pc() - code->instruction_start());
1340 AbstractCode* abstract_code = AbstractCode::cast(code); 1359 AbstractCode* abstract_code = AbstractCode::cast(code);
1341 Handle<JSFunction> fun(function(), isolate()); 1360 Handle<JSFunction> fun(function(), isolate());
1342 FrameSummary summary(receiver(), *fun, abstract_code, offset, false); 1361 FrameSummary summary(receiver(), *fun, abstract_code, offset, false);
1343 functions->Add(summary); 1362 functions->Add(summary);
1344 } 1363 }
1345 1364
1346 void WasmFrame::Iterate(ObjectVisitor* v) const { IterateCompiledFrame(v); } 1365 void WasmFrame::Iterate(ObjectVisitor* v) const { IterateCompiledFrame(v); }
(...skipping 432 matching lines...) Expand 10 before | Expand all | Expand 10 after
1779 for (StackFrameIterator it(isolate); !it.done(); it.Advance()) { 1798 for (StackFrameIterator it(isolate); !it.done(); it.Advance()) {
1780 StackFrame* frame = AllocateFrameCopy(it.frame(), zone); 1799 StackFrame* frame = AllocateFrameCopy(it.frame(), zone);
1781 list.Add(frame, zone); 1800 list.Add(frame, zone);
1782 } 1801 }
1783 return list.ToVector(); 1802 return list.ToVector();
1784 } 1803 }
1785 1804
1786 1805
1787 } // namespace internal 1806 } // namespace internal
1788 } // namespace v8 1807 } // namespace v8
OLDNEW
« no previous file with comments | « src/frames.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698