LCOV - code coverage report
Current view: top level - src/compiler - frame-states.cc (source / functions) Hit Total Coverage
Test: app.info Lines: 38 69 55.1 %
Date: 2017-10-20 Functions: 6 10 60.0 %

          Line data    Source code
       1             : // Copyright 2015 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/compiler/frame-states.h"
       6             : 
       7             : #include "src/base/functional.h"
       8             : #include "src/callable.h"
       9             : #include "src/compiler/graph.h"
      10             : #include "src/compiler/js-graph.h"
      11             : #include "src/compiler/node.h"
      12             : #include "src/handles-inl.h"
      13             : #include "src/objects-inl.h"
      14             : 
      15             : namespace v8 {
      16             : namespace internal {
      17             : namespace compiler {
      18             : 
      19    24853692 : size_t hash_value(OutputFrameStateCombine const& sc) {
      20    24853692 :   return base::hash_value(sc.parameter_);
      21             : }
      22             : 
      23             : 
      24           0 : std::ostream& operator<<(std::ostream& os, OutputFrameStateCombine const& sc) {
      25           0 :   if (sc.parameter_ == OutputFrameStateCombine::kInvalidIndex)
      26           0 :     return os << "Ignore";
      27           0 :   return os << "PokeAt(" << sc.parameter_ << ")";
      28             : }
      29             : 
      30             : 
      31    14997892 : bool operator==(FrameStateInfo const& lhs, FrameStateInfo const& rhs) {
      32     7422863 :   return lhs.type() == rhs.type() && lhs.bailout_id() == rhs.bailout_id() &&
      33     8042868 :          lhs.state_combine() == rhs.state_combine() &&
      34     7498946 :          lhs.function_info() == rhs.function_info();
      35             : }
      36             : 
      37             : 
      38           0 : bool operator!=(FrameStateInfo const& lhs, FrameStateInfo const& rhs) {
      39           0 :   return !(lhs == rhs);
      40             : }
      41             : 
      42             : 
      43    49707624 : size_t hash_value(FrameStateInfo const& info) {
      44             :   return base::hash_combine(static_cast<int>(info.type()), info.bailout_id(),
      45    49707298 :                             info.state_combine());
      46             : }
      47             : 
      48             : 
      49           0 : std::ostream& operator<<(std::ostream& os, FrameStateType type) {
      50           0 :   switch (type) {
      51             :     case FrameStateType::kInterpretedFunction:
      52           0 :       os << "INTERPRETED_FRAME";
      53           0 :       break;
      54             :     case FrameStateType::kArgumentsAdaptor:
      55           0 :       os << "ARGUMENTS_ADAPTOR";
      56           0 :       break;
      57             :     case FrameStateType::kConstructStub:
      58           0 :       os << "CONSTRUCT_STUB";
      59           0 :       break;
      60             :     case FrameStateType::kBuiltinContinuation:
      61           0 :       os << "BUILTIN_CONTINUATION_FRAME";
      62           0 :       break;
      63             :     case FrameStateType::kJavaScriptBuiltinContinuation:
      64           0 :       os << "JAVA_SCRIPT_BUILTIN_CONTINUATION_FRAME";
      65           0 :       break;
      66             :     case FrameStateType::kGetterStub:
      67           0 :       os << "GETTER_STUB";
      68           0 :       break;
      69             :     case FrameStateType::kSetterStub:
      70           0 :       os << "SETTER_STUB";
      71           0 :       break;
      72             :   }
      73           0 :   return os;
      74             : }
      75             : 
      76             : 
      77           0 : std::ostream& operator<<(std::ostream& os, FrameStateInfo const& info) {
      78           0 :   os << info.type() << ", " << info.bailout_id() << ", "
      79           0 :      << info.state_combine();
      80             :   Handle<SharedFunctionInfo> shared_info;
      81           0 :   if (info.shared_info().ToHandle(&shared_info)) {
      82           0 :     os << ", " << Brief(*shared_info);
      83             :   }
      84           0 :   return os;
      85             : }
      86             : 
      87             : namespace {
      88        2935 : Node* CreateBuiltinContinuationFrameStateCommon(
      89        2935 :     JSGraph* js_graph, Builtins::Name name, Node* context, Node** parameters,
      90             :     int parameter_count, Node* outer_frame_state, Handle<JSFunction> function) {
      91             :   Isolate* isolate = js_graph->isolate();
      92             :   Graph* graph = js_graph->graph();
      93             :   CommonOperatorBuilder* common = js_graph->common();
      94             : 
      95        2935 :   BailoutId bailout_id = Builtins::GetContinuationBailoutId(name);
      96        2935 :   Callable callable = Builtins::CallableFor(isolate, name);
      97             : 
      98             :   const Operator* op_param =
      99        2935 :       common->StateValues(parameter_count, SparseInputMask::Dense());
     100        2935 :   Node* params_node = graph->NewNode(op_param, parameter_count, parameters);
     101             : 
     102             :   FrameStateType frame_type =
     103             :       function.is_null() ? FrameStateType::kBuiltinContinuation
     104        2935 :                          : FrameStateType::kJavaScriptBuiltinContinuation;
     105             :   const FrameStateFunctionInfo* state_info =
     106             :       common->CreateFrameStateFunctionInfo(
     107             :           frame_type, parameter_count, 0,
     108             :           function.is_null() ? Handle<SharedFunctionInfo>()
     109        4162 :                              : Handle<SharedFunctionInfo>(function->shared()));
     110             :   const Operator* op = common->FrameState(
     111        2935 :       bailout_id, OutputFrameStateCombine::Ignore(), state_info);
     112             : 
     113             :   Node* function_node = function.is_null() ? js_graph->UndefinedConstant()
     114        4162 :                                            : js_graph->HeapConstant(function);
     115             : 
     116             :   Node* frame_state = graph->NewNode(
     117             :       op, params_node, js_graph->EmptyStateValues(),
     118        2935 :       js_graph->EmptyStateValues(), context, function_node, outer_frame_state);
     119             : 
     120        2935 :   return frame_state;
     121             : }
     122             : }  // namespace
     123             : 
     124        1708 : Node* CreateStubBuiltinContinuationFrameState(JSGraph* js_graph,
     125             :                                               Builtins::Name name,
     126             :                                               Node* context, Node** parameters,
     127             :                                               int parameter_count,
     128             :                                               Node* outer_frame_state,
     129             :                                               ContinuationFrameStateMode mode) {
     130             :   Isolate* isolate = js_graph->isolate();
     131        1708 :   Callable callable = Builtins::CallableFor(isolate, name);
     132             :   CallInterfaceDescriptor descriptor = callable.descriptor();
     133             : 
     134             :   std::vector<Node*> actual_parameters;
     135             :   // Stack parameters first. If the deoptimization is LAZY, the final parameter
     136             :   // is added by the deoptimizer and isn't explicitly passed in the frame state.
     137             :   int stack_parameter_count =
     138        1708 :       descriptor.GetRegisterParameterCount() -
     139        1708 :       (mode == ContinuationFrameStateMode::LAZY ? 1 : 0);
     140        1708 :   for (int i = 0; i < stack_parameter_count; ++i) {
     141             :     actual_parameters.push_back(
     142           0 :         parameters[descriptor.GetRegisterParameterCount() + i]);
     143             :   }
     144             :   // Register parameters follow, context will be added by instruction selector
     145             :   // during FrameState translation.
     146        1708 :   for (int i = 0; i < descriptor.GetRegisterParameterCount(); ++i) {
     147           0 :     actual_parameters.push_back(parameters[i]);
     148             :   }
     149             : 
     150             :   return CreateBuiltinContinuationFrameStateCommon(
     151             :       js_graph, name, context, actual_parameters.data(),
     152        1708 :       static_cast<int>(actual_parameters.size()), outer_frame_state,
     153        3416 :       Handle<JSFunction>());
     154             : }
     155             : 
     156        1227 : Node* CreateJavaScriptBuiltinContinuationFrameState(
     157        1227 :     JSGraph* js_graph, Handle<JSFunction> function, Builtins::Name name,
     158             :     Node* target, Node* context, Node** stack_parameters,
     159             :     int stack_parameter_count, Node* outer_frame_state,
     160             :     ContinuationFrameStateMode mode) {
     161             :   Isolate* isolate = js_graph->isolate();
     162        1227 :   Callable callable = Builtins::CallableFor(isolate, name);
     163             : 
     164             :   // Lazy deopt points where the frame state is assocated with a call get an
     165             :   // additional parameter for the return result from the call that's added by
     166             :   // the deoptimizer and not explicitly specified in the frame state. Check that
     167             :   // there is not a mismatch between the number of frame state parameters and
     168             :   // the stack parameters required by the builtin taking this into account.
     169             :   DCHECK_EQ(Builtins::GetStackParameterCount(name) + 1,  // add receiver
     170             :             stack_parameter_count +
     171             :                 (mode == ContinuationFrameStateMode::EAGER ? 0 : 1));
     172             : 
     173             :   Node* argc =
     174             :       js_graph->Constant(stack_parameter_count -
     175        1227 :                          (mode == ContinuationFrameStateMode::EAGER ? 1 : 0));
     176             : 
     177             :   // Stack parameters first. They must be first because the receiver is expected
     178             :   // to be the second value in the translation when creating stack crawls
     179             :   // (e.g. Error.stack) of optimized JavaScript frames.
     180             :   std::vector<Node*> actual_parameters;
     181        7881 :   for (int i = 0; i < stack_parameter_count; ++i) {
     182        6654 :     actual_parameters.push_back(stack_parameters[i]);
     183             :   }
     184             : 
     185             :   // Register parameters follow stack paraemters. The context will be added by
     186             :   // instruction selector during FrameState translation.
     187        1227 :   actual_parameters.push_back(target);
     188        2454 :   actual_parameters.push_back(js_graph->UndefinedConstant());
     189        1227 :   actual_parameters.push_back(argc);
     190             : 
     191             :   return CreateBuiltinContinuationFrameStateCommon(
     192             :       js_graph, name, context, &actual_parameters[0],
     193        3681 :       static_cast<int>(actual_parameters.size()), outer_frame_state, function);
     194             : }
     195             : 
     196             : }  // namespace compiler
     197             : }  // namespace internal
     198             : }  // namespace v8

Generated by: LCOV version 1.10