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

Side by Side Diff: runtime/vm/object.cc

Issue 1582683003: Fall back to inlining intervals to generate stack traces in --noopt. Inlined frames will lack line … (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: Created 4 years, 11 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
OLDNEW
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #include "vm/object.h" 5 #include "vm/object.h"
6 6
7 #include "include/dart_api.h" 7 #include "include/dart_api.h"
8 #include "platform/assert.h" 8 #include "platform/assert.h"
9 #include "vm/assembler.h" 9 #include "vm/assembler.h"
10 #include "vm/cpu.h" 10 #include "vm/cpu.h"
(...skipping 21582 matching lines...) Expand 10 before | Expand all | Expand 10 after
21593 } else { 21593 } else {
21594 chars = OS::SCreate(zone, 21594 chars = OS::SCreate(zone,
21595 "#%-6" Pd " %s (%s)\n", 21595 "#%-6" Pd " %s (%s)\n",
21596 frame_index, function_name.ToCString(), url.ToCString()); 21596 frame_index, function_name.ToCString(), url.ToCString());
21597 } 21597 }
21598 frame_strings->Add(chars); 21598 frame_strings->Add(chars);
21599 return strlen(chars); 21599 return strlen(chars);
21600 } 21600 }
21601 21601
21602 21602
21603 static intptr_t PrintOneStacktraceNoCode(Zone* zone,
21604 GrowableArray<char*>* frame_strings,
21605 const Function& function,
21606 intptr_t frame_index) {
21607 const Script& script = Script::Handle(zone, function.script());
21608 const String& function_name =
21609 String::Handle(zone, function.QualifiedUserVisibleName());
21610 const String& url = String::Handle(zone, script.url());
21611 char* chars = NULL;
21612 chars = OS::SCreate(zone,
21613 "#%-6" Pd " %s (%s)\n",
21614 frame_index, function_name.ToCString(), url.ToCString());
21615 frame_strings->Add(chars);
21616 return strlen(chars);
21617 }
21618
21619
21603 const char* Stacktrace::ToCStringInternal(intptr_t* frame_index, 21620 const char* Stacktrace::ToCStringInternal(intptr_t* frame_index,
21604 intptr_t max_frames) const { 21621 intptr_t max_frames) const {
21605 Zone* zone = Thread::Current()->zone(); 21622 Zone* zone = Thread::Current()->zone();
21606 Function& function = Function::Handle(); 21623 Function& function = Function::Handle();
21607 Code& code = Code::Handle(); 21624 Code& code = Code::Handle();
21608 // Iterate through the stack frames and create C string description 21625 // Iterate through the stack frames and create C string description
21609 // for each frame. 21626 // for each frame.
21610 intptr_t total_len = 0; 21627 intptr_t total_len = 0;
21611 GrowableArray<char*> frame_strings; 21628 GrowableArray<char*> frame_strings;
21612 for (intptr_t i = 0; (i < Length()) && (*frame_index < max_frames); i++) { 21629 for (intptr_t i = 0; (i < Length()) && (*frame_index < max_frames); i++) {
21613 function = FunctionAtFrame(i); 21630 function = FunctionAtFrame(i);
21614 if (function.IsNull()) { 21631 if (function.IsNull()) {
21615 // Check if null function object indicates a stack trace overflow. 21632 // Check if null function object indicates a gap in a StackOverflow or
21633 // OutOfMemory trace.
21616 if ((i < (Length() - 1)) && 21634 if ((i < (Length() - 1)) &&
21617 (FunctionAtFrame(i + 1) != Function::null())) { 21635 (FunctionAtFrame(i + 1) != Function::null())) {
21618 const char* kTruncated = "...\n...\n"; 21636 const char* kTruncated = "...\n...\n";
21619 intptr_t truncated_len = strlen(kTruncated) + 1; 21637 intptr_t truncated_len = strlen(kTruncated) + 1;
21620 char* chars = zone->Alloc<char>(truncated_len); 21638 char* chars = zone->Alloc<char>(truncated_len);
21621 OS::SNPrint(chars, truncated_len, "%s", kTruncated); 21639 OS::SNPrint(chars, truncated_len, "%s", kTruncated);
21622 frame_strings.Add(chars); 21640 frame_strings.Add(chars);
21623 total_len += truncated_len; 21641 total_len += truncated_len;
21624 } 21642 }
21625 } else if (function.is_visible() || FLAG_show_invisible_frames) { 21643 } else {
21626 code = CodeAtFrame(i); 21644 code = CodeAtFrame(i);
21627 ASSERT(function.raw() == code.function()); 21645 ASSERT(function.raw() == code.function());
21628 uword pc = code.EntryPoint() + Smi::Value(PcOffsetAtFrame(i)); 21646 uword pc = code.EntryPoint() + Smi::Value(PcOffsetAtFrame(i));
21629 if (code.is_optimized() && expand_inlined()) { 21647 if (code.is_optimized() && expand_inlined()) {
21630 // Traverse inlined frames. 21648 // Traverse inlined frames.
21631 for (InlinedFunctionsIterator it(code, pc); 21649 if (Compiler::allow_recompilation()) {
21632 !it.Done() && (*frame_index < max_frames); it.Advance()) { 21650 for (InlinedFunctionsIterator it(code, pc);
21633 function = it.function(); 21651 !it.Done() && (*frame_index < max_frames); it.Advance()) {
21634 if (function.is_visible() || FLAG_show_invisible_frames) { 21652 function = it.function();
21635 code = it.code(); 21653 if (function.is_visible() || FLAG_show_invisible_frames) {
21636 ASSERT(function.raw() == code.function()); 21654 code = it.code();
21637 uword pc = it.pc(); 21655 ASSERT(function.raw() == code.function());
21638 ASSERT(pc != 0); 21656 uword pc = it.pc();
21639 ASSERT(code.EntryPoint() <= pc); 21657 ASSERT(pc != 0);
21640 ASSERT(pc < (code.EntryPoint() + code.Size())); 21658 ASSERT(code.EntryPoint() <= pc);
21641 total_len += PrintOneStacktrace( 21659 ASSERT(pc < (code.EntryPoint() + code.Size()));
21642 zone, &frame_strings, pc, function, code, *frame_index); 21660 total_len += PrintOneStacktrace(
21643 (*frame_index)++; // To account for inlined frames. 21661 zone, &frame_strings, pc, function, code, *frame_index);
21662 (*frame_index)++; // To account for inlined frames.
21663 }
21664 }
21665 } else {
21666 // Precompilation: we don't have deopt info, so we don't know the
21667 // source position of inlined functions, but we can still name them.
21668 intptr_t offset = Smi::Value(PcOffsetAtFrame(i));
21669 // The PC of frames below the top frame is a call's return address,
21670 // which can belong to a different inlining interval than the call.
21671 intptr_t effective_offset = offset - 1;
21672 GrowableArray<Function*> inlined_functions;
21673 code.GetInlinedFunctionsAt(effective_offset, &inlined_functions);
21674 ASSERT(inlined_functions.length() >= 1); // At least the inliner.
21675 for (intptr_t j = 0; j < inlined_functions.length(); j++) {
21676 Function* inlined_function = inlined_functions[j];
21677 ASSERT(inlined_function != NULL);
21678 ASSERT(!inlined_function->IsNull());
21679 if (inlined_function->is_visible() || FLAG_show_invisible_frames) {
21680 total_len += PrintOneStacktraceNoCode(
21681 zone, &frame_strings, *inlined_function, *frame_index);
21682 (*frame_index)++;
21683 }
21644 } 21684 }
21645 } 21685 }
21646 } else { 21686 } else {
21647 total_len += PrintOneStacktrace( 21687 if (function.is_visible() || FLAG_show_invisible_frames) {
21648 zone, &frame_strings, pc, function, code, *frame_index); 21688 total_len += PrintOneStacktrace(
21649 (*frame_index)++; 21689 zone, &frame_strings, pc, function, code, *frame_index);
21690 (*frame_index)++;
21691 }
21650 } 21692 }
21651 } 21693 }
21652 } 21694 }
21653 21695
21654 // Now concatenate the frame descriptions into a single C string. 21696 // Now concatenate the frame descriptions into a single C string.
21655 char* chars = zone->Alloc<char>(total_len + 1); 21697 char* chars = zone->Alloc<char>(total_len + 1);
21656 intptr_t index = 0; 21698 intptr_t index = 0;
21657 for (intptr_t i = 0; i < frame_strings.length(); i++) { 21699 for (intptr_t i = 0; i < frame_strings.length(); i++) {
21658 index += OS::SNPrint((chars + index), 21700 index += OS::SNPrint((chars + index),
21659 (total_len + 1 - index), 21701 (total_len + 1 - index),
(...skipping 373 matching lines...) Expand 10 before | Expand all | Expand 10 after
22033 return tag_label.ToCString(); 22075 return tag_label.ToCString();
22034 } 22076 }
22035 22077
22036 22078
22037 void UserTag::PrintJSONImpl(JSONStream* stream, bool ref) const { 22079 void UserTag::PrintJSONImpl(JSONStream* stream, bool ref) const {
22038 Instance::PrintJSONImpl(stream, ref); 22080 Instance::PrintJSONImpl(stream, ref);
22039 } 22081 }
22040 22082
22041 22083
22042 } // namespace dart 22084 } // namespace dart
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698