| OLD | NEW |
| (Empty) |
| 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/control-reducer.h" | |
| 6 #include "src/compiler/diamond.h" | |
| 7 #include "src/compiler/graph-visualizer.h" | |
| 8 #include "src/compiler/js-graph.h" | |
| 9 #include "src/compiler/js-operator.h" | |
| 10 #include "src/compiler/machine-operator.h" | |
| 11 #include "src/compiler/node.h" | |
| 12 #include "test/unittests/compiler/graph-unittest.h" | |
| 13 #include "test/unittests/compiler/node-test-utils.h" | |
| 14 #include "testing/gmock-support.h" | |
| 15 | |
| 16 using testing::_; | |
| 17 using testing::AllOf; | |
| 18 using testing::Capture; | |
| 19 using testing::CaptureEq; | |
| 20 | |
| 21 namespace v8 { | |
| 22 namespace internal { | |
| 23 namespace compiler { | |
| 24 | |
| 25 class ControlReducerTest : public GraphTest { | |
| 26 public: | |
| 27 ControlReducerTest() | |
| 28 : GraphTest(1), | |
| 29 machine_(zone()), | |
| 30 javascript_(zone()), | |
| 31 jsgraph_(isolate(), graph(), common(), &javascript_, &machine_) {} | |
| 32 | |
| 33 protected: | |
| 34 MachineOperatorBuilder machine_; | |
| 35 JSOperatorBuilder javascript_; | |
| 36 JSGraph jsgraph_; | |
| 37 | |
| 38 void ReduceGraph(int max_phis_for_select = 0) { | |
| 39 if (FLAG_trace_turbo_graph) { | |
| 40 OFStream os(stdout); | |
| 41 os << "-- Graph before control reduction" << std::endl; | |
| 42 os << AsRPO(*graph()); | |
| 43 } | |
| 44 ControlReducer::ReduceGraph(zone(), jsgraph(), max_phis_for_select); | |
| 45 if (FLAG_trace_turbo_graph) { | |
| 46 OFStream os(stdout); | |
| 47 os << "-- Graph after control reduction" << std::endl; | |
| 48 os << AsRPO(*graph()); | |
| 49 } | |
| 50 } | |
| 51 | |
| 52 JSGraph* jsgraph() { return &jsgraph_; } | |
| 53 }; | |
| 54 | |
| 55 | |
| 56 TEST_F(ControlReducerTest, SelectPhi) { | |
| 57 Node* p0 = Parameter(0); | |
| 58 const MachineType kType = kMachInt32; | |
| 59 Diamond d(graph(), common(), p0); | |
| 60 Node* phi = | |
| 61 d.Phi(kType, jsgraph()->Int32Constant(1), jsgraph()->Int32Constant(2)); | |
| 62 | |
| 63 Node* ret = | |
| 64 graph()->NewNode(common()->Return(), phi, graph()->start(), d.merge); | |
| 65 graph()->end()->ReplaceInput(0, ret); | |
| 66 | |
| 67 ReduceGraph(1); | |
| 68 | |
| 69 // Phi should be replaced with a select. | |
| 70 EXPECT_THAT(graph()->end(), | |
| 71 IsEnd(IsReturn( | |
| 72 IsSelect(kType, p0, IsInt32Constant(1), IsInt32Constant(2)), | |
| 73 graph()->start(), graph()->start()))); | |
| 74 } | |
| 75 | |
| 76 | |
| 77 TEST_F(ControlReducerTest, SelectPhis_fail) { | |
| 78 Node* p0 = Parameter(0); | |
| 79 const MachineType kType = kMachInt32; | |
| 80 Diamond d(graph(), common(), p0); | |
| 81 Node* phi = | |
| 82 d.Phi(kType, jsgraph()->Int32Constant(1), jsgraph()->Int32Constant(2)); | |
| 83 Node* phi2 = | |
| 84 d.Phi(kType, jsgraph()->Int32Constant(11), jsgraph()->Int32Constant(22)); | |
| 85 USE(phi2); | |
| 86 Node* ret = | |
| 87 graph()->NewNode(common()->Return(), phi, graph()->start(), d.merge); | |
| 88 graph()->end()->ReplaceInput(0, ret); | |
| 89 | |
| 90 ReduceGraph(1); | |
| 91 | |
| 92 // Diamond should not be replaced with a select (too many phis). | |
| 93 EXPECT_THAT(ret, IsReturn(phi, graph()->start(), d.merge)); | |
| 94 EXPECT_THAT(graph()->end(), IsEnd(ret)); | |
| 95 } | |
| 96 | |
| 97 | |
| 98 TEST_F(ControlReducerTest, SelectTwoPhis) { | |
| 99 Node* p0 = Parameter(0); | |
| 100 const MachineType kType = kMachInt32; | |
| 101 Diamond d(graph(), common(), p0); | |
| 102 Node* phi1 = | |
| 103 d.Phi(kType, jsgraph()->Int32Constant(1), jsgraph()->Int32Constant(2)); | |
| 104 Node* phi2 = | |
| 105 d.Phi(kType, jsgraph()->Int32Constant(2), jsgraph()->Int32Constant(3)); | |
| 106 MachineOperatorBuilder machine(zone()); | |
| 107 Node* add = graph()->NewNode(machine.Int32Add(), phi1, phi2); | |
| 108 Node* ret = | |
| 109 graph()->NewNode(common()->Return(), add, graph()->start(), d.merge); | |
| 110 graph()->end()->ReplaceInput(0, ret); | |
| 111 | |
| 112 ReduceGraph(2); | |
| 113 | |
| 114 // Phis should be replaced with two selects. | |
| 115 EXPECT_THAT( | |
| 116 ret, | |
| 117 IsReturn(IsInt32Add( | |
| 118 IsSelect(kType, p0, IsInt32Constant(1), IsInt32Constant(2)), | |
| 119 IsSelect(kType, p0, IsInt32Constant(2), IsInt32Constant(3))), | |
| 120 graph()->start(), graph()->start())); | |
| 121 EXPECT_THAT(graph()->end(), IsEnd(ret)); | |
| 122 } | |
| 123 | |
| 124 } // namespace compiler | |
| 125 } // namespace internal | |
| 126 } // namespace v8 | |
| OLD | NEW |