LCOV - code coverage report
Current view: top level - src/debug - debug-stack-trace-iterator.cc (source / functions) Hit Total Coverage
Test: app.info Lines: 67 67 100.0 %
Date: 2017-10-20 Functions: 16 16 100.0 %

          Line data    Source code
       1             : // Copyright 2017 the V8 project authors. All rights reserved.
       2             : // Use of this source code is governed by a BSD-style license that can be
       3             : // found in the LICENSE file.
       4             : 
       5             : #include "src/debug/debug-stack-trace-iterator.h"
       6             : 
       7             : #include "src/api.h"
       8             : #include "src/debug/debug-evaluate.h"
       9             : #include "src/debug/debug-scope-iterator.h"
      10             : #include "src/debug/debug.h"
      11             : #include "src/debug/liveedit.h"
      12             : #include "src/frames-inl.h"
      13             : #include "src/isolate.h"
      14             : 
      15             : namespace v8 {
      16             : 
      17       59807 : std::unique_ptr<debug::StackTraceIterator> debug::StackTraceIterator::Create(
      18             :     v8::Isolate* isolate, int index) {
      19             :   return std::unique_ptr<debug::StackTraceIterator>(
      20             :       new internal::DebugStackTraceIterator(
      21      119614 :           reinterpret_cast<internal::Isolate*>(isolate), index));
      22             : }
      23             : 
      24             : namespace internal {
      25             : 
      26      119614 : DebugStackTraceIterator::DebugStackTraceIterator(Isolate* isolate, int index)
      27             :     : isolate_(isolate),
      28             :       iterator_(isolate, isolate->debug()->break_frame_id()),
      29      119614 :       is_top_frame_(true) {
      30       59807 :   if (iterator_.done()) return;
      31             :   std::vector<FrameSummary> frames;
      32       59807 :   frames.reserve(FLAG_max_inlining_levels + 1);
      33       59807 :   iterator_.frame()->Summarize(&frames);
      34      119614 :   inlined_frame_index_ = static_cast<int>(frames.size());
      35       59807 :   Advance();
      36      128337 :   for (; !Done() && index > 0; --index) Advance();
      37             : }
      38             : 
      39      179421 : DebugStackTraceIterator::~DebugStackTraceIterator() {}
      40             : 
      41      369770 : bool DebugStackTraceIterator::Done() const { return iterator_.done(); }
      42             : 
      43      193608 : void DebugStackTraceIterator::Advance() {
      44             :   while (true) {
      45      271108 :     --inlined_frame_index_;
      46      271136 :     for (; inlined_frame_index_ >= 0; --inlined_frame_index_) {
      47             :       // Omit functions from native and extension scripts.
      48      287580 :       if (FrameSummary::Get(iterator_.frame(), inlined_frame_index_)
      49      287580 :               .is_subject_to_debugging()) {
      50             :         break;
      51             :       }
      52          28 :       is_top_frame_ = false;
      53             :     }
      54      271108 :     if (inlined_frame_index_ >= 0) {
      55             :       frame_inspector_.reset(new FrameInspector(
      56      143762 :           iterator_.frame(), inlined_frame_index_, isolate_));
      57      193608 :       break;
      58             :     }
      59      127346 :     is_top_frame_ = false;
      60             :     frame_inspector_.reset();
      61      127346 :     iterator_.Advance();
      62      127346 :     if (iterator_.done()) break;
      63             :     std::vector<FrameSummary> frames;
      64       77500 :     frames.reserve(FLAG_max_inlining_levels + 1);
      65       77500 :     iterator_.frame()->Summarize(&frames);
      66      155000 :     inlined_frame_index_ = static_cast<int>(frames.size());
      67       77500 :   }
      68      193608 : }
      69             : 
      70      125171 : int DebugStackTraceIterator::GetContextId() const {
      71             :   DCHECK(!Done());
      72      125171 :   Handle<Object> context = frame_inspector_->GetContext();
      73      125171 :   if (context->IsContext()) {
      74             :     Object* value =
      75             :         Context::cast(*context)->native_context()->debug_context_id();
      76      250114 :     if (value->IsSmi()) return Smi::ToInt(value);
      77             :   }
      78             :   return 0;
      79             : }
      80             : 
      81      124988 : v8::Local<v8::Value> DebugStackTraceIterator::GetReceiver() const {
      82             :   DCHECK(!Done());
      83             :   Handle<Object> value = frame_inspector_->GetReceiver();
      84      374955 :   if (value.is_null() || (value->IsSmi() || !value->IsTheHole(isolate_))) {
      85             :     return Utils::ToLocal(value);
      86             :   }
      87         570 :   return v8::Undefined(reinterpret_cast<v8::Isolate*>(isolate_));
      88             : }
      89             : 
      90      125078 : v8::Local<v8::Value> DebugStackTraceIterator::GetReturnValue() const {
      91             :   DCHECK(!Done());
      92      125078 :   if (frame_inspector_->IsWasm()) return v8::Local<v8::Value>();
      93      124682 :   bool is_optimized = iterator_.frame()->is_optimized();
      94      173146 :   if (is_optimized || !is_top_frame_ ||
      95       53963 :       !isolate_->debug()->IsBreakAtReturn(iterator_.javascript_frame())) {
      96      119183 :     return v8::Local<v8::Value>();
      97             :   }
      98       10998 :   return Utils::ToLocal(isolate_->debug()->return_value_handle());
      99             : }
     100             : 
     101      125078 : v8::Local<v8::String> DebugStackTraceIterator::GetFunctionName() const {
     102             :   DCHECK(!Done());
     103      125078 :   return Utils::ToLocal(frame_inspector_->GetFunctionName());
     104             : }
     105             : 
     106      250249 : v8::Local<v8::debug::Script> DebugStackTraceIterator::GetScript() const {
     107             :   DCHECK(!Done());
     108             :   Handle<Object> value = frame_inspector_->GetScript();
     109      250249 :   if (!value->IsScript()) return v8::Local<v8::debug::Script>();
     110             :   return ToApiHandle<debug::Script>(Handle<Script>::cast(value));
     111             : }
     112             : 
     113      125171 : debug::Location DebugStackTraceIterator::GetSourceLocation() const {
     114             :   DCHECK(!Done());
     115      125171 :   v8::Local<v8::debug::Script> script = GetScript();
     116      125171 :   if (script.IsEmpty()) return v8::debug::Location();
     117      125171 :   return script->GetSourceLocation(frame_inspector_->GetSourcePosition());
     118             : }
     119             : 
     120      125078 : v8::Local<v8::Function> DebugStackTraceIterator::GetFunction() const {
     121             :   DCHECK(!Done());
     122      125078 :   if (!frame_inspector_->IsJavaScript()) return v8::Local<v8::Function>();
     123             :   return Utils::ToLocal(frame_inspector_->GetFunction());
     124             : }
     125             : 
     126             : std::unique_ptr<v8::debug::ScopeIterator>
     127      125387 : DebugStackTraceIterator::GetScopeIterator() const {
     128             :   DCHECK(!Done());
     129             :   StandardFrame* frame = iterator_.frame();
     130      250774 :   if (frame->is_wasm_interpreter_entry()) {
     131             :     return std::unique_ptr<v8::debug::ScopeIterator>(new DebugWasmScopeIterator(
     132         285 :         isolate_, iterator_.frame(), inlined_frame_index_));
     133             :   }
     134             :   return std::unique_ptr<v8::debug::ScopeIterator>(
     135      125102 :       new DebugScopeIterator(isolate_, frame_inspector_.get()));
     136             : }
     137             : 
     138          99 : bool DebugStackTraceIterator::Restart() {
     139             :   DCHECK(!Done());
     140          99 :   if (iterator_.is_wasm()) return false;
     141          99 :   return !LiveEdit::RestartFrame(iterator_.javascript_frame());
     142             : }
     143             : 
     144        9553 : v8::MaybeLocal<v8::Value> DebugStackTraceIterator::Evaluate(
     145             :     v8::Local<v8::String> source, bool throw_on_side_effect) {
     146             :   DCHECK(!Done());
     147             :   Handle<Object> value;
     148        9553 :   if (!DebugEvaluate::Local(isolate_, iterator_.frame()->id(),
     149             :                             inlined_frame_index_, Utils::OpenHandle(*source),
     150       38212 :                             throw_on_side_effect)
     151       19106 :            .ToHandle(&value)) {
     152         912 :     isolate_->OptionalRescheduleException(false);
     153         912 :     return v8::MaybeLocal<v8::Value>();
     154             :   }
     155        8641 :   return Utils::ToLocal(value);
     156             : }
     157             : }  // namespace internal
     158             : }  // namespace v8

Generated by: LCOV version 1.10