Home | History | Annotate | Download | only in compiler
      1 // Copyright 2014 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/generic-node-inl.h"
      6 #include "src/compiler/js-graph.h"
      7 #include "src/compiler/machine-operator.h"
      8 #include "src/compiler/node-matchers.h"
      9 #include "src/compiler/simplified-operator-reducer.h"
     10 
     11 namespace v8 {
     12 namespace internal {
     13 namespace compiler {
     14 
     15 SimplifiedOperatorReducer::~SimplifiedOperatorReducer() {}
     16 
     17 
     18 Reduction SimplifiedOperatorReducer::Reduce(Node* node) {
     19   switch (node->opcode()) {
     20     case IrOpcode::kBooleanNot: {
     21       HeapObjectMatcher<HeapObject> m(node->InputAt(0));
     22       if (m.Is(Unique<HeapObject>::CreateImmovable(factory()->false_value()))) {
     23         return Replace(jsgraph()->TrueConstant());
     24       }
     25       if (m.Is(Unique<HeapObject>::CreateImmovable(factory()->true_value()))) {
     26         return Replace(jsgraph()->FalseConstant());
     27       }
     28       if (m.IsBooleanNot()) return Replace(m.node()->InputAt(0));
     29       break;
     30     }
     31     case IrOpcode::kChangeBitToBool: {
     32       Int32Matcher m(node->InputAt(0));
     33       if (m.Is(0)) return Replace(jsgraph()->FalseConstant());
     34       if (m.Is(1)) return Replace(jsgraph()->TrueConstant());
     35       if (m.IsChangeBoolToBit()) return Replace(m.node()->InputAt(0));
     36       break;
     37     }
     38     case IrOpcode::kChangeBoolToBit: {
     39       HeapObjectMatcher<HeapObject> m(node->InputAt(0));
     40       if (m.Is(Unique<HeapObject>::CreateImmovable(factory()->false_value()))) {
     41         return ReplaceInt32(0);
     42       }
     43       if (m.Is(Unique<HeapObject>::CreateImmovable(factory()->true_value()))) {
     44         return ReplaceInt32(1);
     45       }
     46       if (m.IsChangeBitToBool()) return Replace(m.node()->InputAt(0));
     47       break;
     48     }
     49     case IrOpcode::kChangeFloat64ToTagged: {
     50       Float64Matcher m(node->InputAt(0));
     51       if (m.HasValue()) return ReplaceNumber(m.Value());
     52       break;
     53     }
     54     case IrOpcode::kChangeInt32ToTagged: {
     55       Int32Matcher m(node->InputAt(0));
     56       if (m.HasValue()) return ReplaceNumber(m.Value());
     57       break;
     58     }
     59     case IrOpcode::kChangeTaggedToFloat64: {
     60       NumberMatcher m(node->InputAt(0));
     61       if (m.HasValue()) return ReplaceFloat64(m.Value());
     62       if (m.IsChangeFloat64ToTagged()) return Replace(m.node()->InputAt(0));
     63       if (m.IsChangeInt32ToTagged()) {
     64         return Change(node, machine()->ChangeInt32ToFloat64(),
     65                       m.node()->InputAt(0));
     66       }
     67       if (m.IsChangeUint32ToTagged()) {
     68         return Change(node, machine()->ChangeUint32ToFloat64(),
     69                       m.node()->InputAt(0));
     70       }
     71       break;
     72     }
     73     case IrOpcode::kChangeTaggedToInt32: {
     74       NumberMatcher m(node->InputAt(0));
     75       if (m.HasValue()) return ReplaceInt32(DoubleToInt32(m.Value()));
     76       if (m.IsChangeFloat64ToTagged()) {
     77         return Change(node, machine()->ChangeFloat64ToInt32(),
     78                       m.node()->InputAt(0));
     79       }
     80       if (m.IsChangeInt32ToTagged()) return Replace(m.node()->InputAt(0));
     81       break;
     82     }
     83     case IrOpcode::kChangeTaggedToUint32: {
     84       NumberMatcher m(node->InputAt(0));
     85       if (m.HasValue()) return ReplaceUint32(DoubleToUint32(m.Value()));
     86       if (m.IsChangeFloat64ToTagged()) {
     87         return Change(node, machine()->ChangeFloat64ToUint32(),
     88                       m.node()->InputAt(0));
     89       }
     90       if (m.IsChangeUint32ToTagged()) return Replace(m.node()->InputAt(0));
     91       break;
     92     }
     93     case IrOpcode::kChangeUint32ToTagged: {
     94       Uint32Matcher m(node->InputAt(0));
     95       if (m.HasValue()) return ReplaceNumber(FastUI2D(m.Value()));
     96       break;
     97     }
     98     default:
     99       break;
    100   }
    101   return NoChange();
    102 }
    103 
    104 
    105 Reduction SimplifiedOperatorReducer::Change(Node* node, const Operator* op,
    106                                             Node* a) {
    107   node->set_op(op);
    108   node->ReplaceInput(0, a);
    109   return Changed(node);
    110 }
    111 
    112 
    113 Reduction SimplifiedOperatorReducer::ReplaceFloat64(double value) {
    114   return Replace(jsgraph()->Float64Constant(value));
    115 }
    116 
    117 
    118 Reduction SimplifiedOperatorReducer::ReplaceInt32(int32_t value) {
    119   return Replace(jsgraph()->Int32Constant(value));
    120 }
    121 
    122 
    123 Reduction SimplifiedOperatorReducer::ReplaceNumber(double value) {
    124   return Replace(jsgraph()->Constant(value));
    125 }
    126 
    127 
    128 Reduction SimplifiedOperatorReducer::ReplaceNumber(int32_t value) {
    129   return Replace(jsgraph()->Constant(value));
    130 }
    131 
    132 
    133 Graph* SimplifiedOperatorReducer::graph() const { return jsgraph()->graph(); }
    134 
    135 
    136 Factory* SimplifiedOperatorReducer::factory() const {
    137   return jsgraph()->isolate()->factory();
    138 }
    139 
    140 
    141 MachineOperatorBuilder* SimplifiedOperatorReducer::machine() const {
    142   return jsgraph()->machine();
    143 }
    144 
    145 }  // namespace compiler
    146 }  // namespace internal
    147 }  // namespace v8
    148