Upstream version 11.40.271.0
[platform/framework/web/crosswalk.git] / src / v8 / test / unittests / compiler / machine-operator-unittest.cc
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/machine-operator.h"
6 #include "src/compiler/operator-properties-inl.h"
7 #include "testing/gtest-support.h"
8
9 namespace v8 {
10 namespace internal {
11 namespace compiler {
12
13 #if GTEST_HAS_COMBINE
14
15 template <typename T>
16 class MachineOperatorTestWithParam
17     : public ::testing::TestWithParam< ::testing::tuple<MachineType, T> > {
18  protected:
19   MachineType type() const { return ::testing::get<0>(B::GetParam()); }
20   const T& GetParam() const { return ::testing::get<1>(B::GetParam()); }
21
22  private:
23   typedef ::testing::TestWithParam< ::testing::tuple<MachineType, T> > B;
24 };
25
26
27 namespace {
28
29 const MachineType kMachineReps[] = {kRepWord32, kRepWord64};
30
31
32 const MachineType kMachineTypes[] = {
33     kMachFloat32, kMachFloat64,   kMachInt8,   kMachUint8,  kMachInt16,
34     kMachUint16,  kMachInt32,     kMachUint32, kMachInt64,  kMachUint64,
35     kMachPtr,     kMachAnyTagged, kRepBit,     kRepWord8,   kRepWord16,
36     kRepWord32,   kRepWord64,     kRepFloat32, kRepFloat64, kRepTagged};
37
38 }  // namespace
39
40
41 // -----------------------------------------------------------------------------
42 // Load operator.
43
44
45 typedef MachineOperatorTestWithParam<LoadRepresentation>
46     MachineLoadOperatorTest;
47
48
49 TEST_P(MachineLoadOperatorTest, InstancesAreGloballyShared) {
50   MachineOperatorBuilder machine1(type());
51   MachineOperatorBuilder machine2(type());
52   EXPECT_EQ(machine1.Load(GetParam()), machine2.Load(GetParam()));
53 }
54
55
56 TEST_P(MachineLoadOperatorTest, NumberOfInputsAndOutputs) {
57   MachineOperatorBuilder machine(type());
58   const Operator* op = machine.Load(GetParam());
59
60   EXPECT_EQ(2, op->ValueInputCount());
61   EXPECT_EQ(1, op->EffectInputCount());
62   EXPECT_EQ(1, op->ControlInputCount());
63   EXPECT_EQ(4, OperatorProperties::GetTotalInputCount(op));
64
65   EXPECT_EQ(1, op->ValueOutputCount());
66   EXPECT_EQ(1, op->EffectOutputCount());
67   EXPECT_EQ(0, op->ControlOutputCount());
68 }
69
70
71 TEST_P(MachineLoadOperatorTest, OpcodeIsCorrect) {
72   MachineOperatorBuilder machine(type());
73   EXPECT_EQ(IrOpcode::kLoad, machine.Load(GetParam())->opcode());
74 }
75
76
77 TEST_P(MachineLoadOperatorTest, ParameterIsCorrect) {
78   MachineOperatorBuilder machine(type());
79   EXPECT_EQ(GetParam(),
80             OpParameter<LoadRepresentation>(machine.Load(GetParam())));
81 }
82
83
84 INSTANTIATE_TEST_CASE_P(MachineOperatorTest, MachineLoadOperatorTest,
85                         ::testing::Combine(::testing::ValuesIn(kMachineReps),
86                                            ::testing::ValuesIn(kMachineTypes)));
87
88
89 // -----------------------------------------------------------------------------
90 // Store operator.
91
92
93 class MachineStoreOperatorTest
94     : public MachineOperatorTestWithParam<
95           ::testing::tuple<MachineType, WriteBarrierKind> > {
96  protected:
97   StoreRepresentation GetParam() const {
98     return StoreRepresentation(
99         ::testing::get<0>(MachineOperatorTestWithParam<
100             ::testing::tuple<MachineType, WriteBarrierKind> >::GetParam()),
101         ::testing::get<1>(MachineOperatorTestWithParam<
102             ::testing::tuple<MachineType, WriteBarrierKind> >::GetParam()));
103   }
104 };
105
106
107 TEST_P(MachineStoreOperatorTest, InstancesAreGloballyShared) {
108   MachineOperatorBuilder machine1(type());
109   MachineOperatorBuilder machine2(type());
110   EXPECT_EQ(machine1.Store(GetParam()), machine2.Store(GetParam()));
111 }
112
113
114 TEST_P(MachineStoreOperatorTest, NumberOfInputsAndOutputs) {
115   MachineOperatorBuilder machine(type());
116   const Operator* op = machine.Store(GetParam());
117
118   EXPECT_EQ(3, op->ValueInputCount());
119   EXPECT_EQ(1, op->EffectInputCount());
120   EXPECT_EQ(1, op->ControlInputCount());
121   EXPECT_EQ(5, OperatorProperties::GetTotalInputCount(op));
122
123   EXPECT_EQ(0, op->ValueOutputCount());
124   EXPECT_EQ(1, op->EffectOutputCount());
125   EXPECT_EQ(0, op->ControlOutputCount());
126 }
127
128
129 TEST_P(MachineStoreOperatorTest, OpcodeIsCorrect) {
130   MachineOperatorBuilder machine(type());
131   EXPECT_EQ(IrOpcode::kStore, machine.Store(GetParam())->opcode());
132 }
133
134
135 TEST_P(MachineStoreOperatorTest, ParameterIsCorrect) {
136   MachineOperatorBuilder machine(type());
137   EXPECT_EQ(GetParam(),
138             OpParameter<StoreRepresentation>(machine.Store(GetParam())));
139 }
140
141
142 INSTANTIATE_TEST_CASE_P(
143     MachineOperatorTest, MachineStoreOperatorTest,
144     ::testing::Combine(
145         ::testing::ValuesIn(kMachineReps),
146         ::testing::Combine(::testing::ValuesIn(kMachineTypes),
147                            ::testing::Values(kNoWriteBarrier,
148                                              kFullWriteBarrier))));
149
150
151 // -----------------------------------------------------------------------------
152 // Pure operators.
153
154
155 namespace {
156
157 struct PureOperator {
158   const Operator* (MachineOperatorBuilder::*constructor)();
159   IrOpcode::Value opcode;
160   int value_input_count;
161   int control_input_count;
162   int value_output_count;
163 };
164
165
166 std::ostream& operator<<(std::ostream& os, const PureOperator& pop) {
167   return os << IrOpcode::Mnemonic(pop.opcode);
168 }
169
170
171 const PureOperator kPureOperators[] = {
172 #define PURE(Name, value_input_count, control_input_count, value_output_count) \
173   {                                                                            \
174     &MachineOperatorBuilder::Name, IrOpcode::k##Name, value_input_count,       \
175         control_input_count, value_output_count                                \
176   }
177     PURE(Word32And, 2, 0, 1), PURE(Word32Or, 2, 0, 1), PURE(Word32Xor, 2, 0, 1),
178     PURE(Word32Shl, 2, 0, 1), PURE(Word32Shr, 2, 0, 1),
179     PURE(Word32Sar, 2, 0, 1), PURE(Word32Ror, 2, 0, 1),
180     PURE(Word32Equal, 2, 0, 1), PURE(Word64And, 2, 0, 1),
181     PURE(Word64Or, 2, 0, 1), PURE(Word64Xor, 2, 0, 1), PURE(Word64Shl, 2, 0, 1),
182     PURE(Word64Shr, 2, 0, 1), PURE(Word64Sar, 2, 0, 1),
183     PURE(Word64Ror, 2, 0, 1), PURE(Word64Equal, 2, 0, 1),
184     PURE(Int32Add, 2, 0, 1), PURE(Int32AddWithOverflow, 2, 0, 2),
185     PURE(Int32Sub, 2, 0, 1), PURE(Int32SubWithOverflow, 2, 0, 2),
186     PURE(Int32Mul, 2, 0, 1), PURE(Int32MulHigh, 2, 0, 1),
187     PURE(Int32Div, 2, 1, 1), PURE(Uint32Div, 2, 1, 1), PURE(Int32Mod, 2, 1, 1),
188     PURE(Uint32Mod, 2, 1, 1), PURE(Int32LessThan, 2, 0, 1),
189     PURE(Int32LessThanOrEqual, 2, 0, 1), PURE(Uint32LessThan, 2, 0, 1),
190     PURE(Uint32LessThanOrEqual, 2, 0, 1), PURE(Int64Add, 2, 0, 1),
191     PURE(Int64Sub, 2, 0, 1), PURE(Int64Mul, 2, 0, 1), PURE(Int64Div, 2, 0, 1),
192     PURE(Uint64Div, 2, 0, 1), PURE(Int64Mod, 2, 0, 1), PURE(Uint64Mod, 2, 0, 1),
193     PURE(Int64LessThan, 2, 0, 1), PURE(Int64LessThanOrEqual, 2, 0, 1),
194     PURE(Uint64LessThan, 2, 0, 1), PURE(ChangeFloat32ToFloat64, 1, 0, 1),
195     PURE(ChangeFloat64ToInt32, 1, 0, 1), PURE(ChangeFloat64ToUint32, 1, 0, 1),
196     PURE(ChangeInt32ToInt64, 1, 0, 1), PURE(ChangeUint32ToFloat64, 1, 0, 1),
197     PURE(ChangeUint32ToUint64, 1, 0, 1),
198     PURE(TruncateFloat64ToFloat32, 1, 0, 1),
199     PURE(TruncateFloat64ToInt32, 1, 0, 1), PURE(TruncateInt64ToInt32, 1, 0, 1),
200     PURE(Float64Add, 2, 0, 1), PURE(Float64Sub, 2, 0, 1),
201     PURE(Float64Mul, 2, 0, 1), PURE(Float64Div, 2, 0, 1),
202     PURE(Float64Mod, 2, 0, 1), PURE(Float64Sqrt, 1, 0, 1),
203     PURE(Float64Equal, 2, 0, 1), PURE(Float64LessThan, 2, 0, 1),
204     PURE(Float64LessThanOrEqual, 2, 0, 1), PURE(LoadStackPointer, 0, 0, 1),
205     PURE(Float64Floor, 1, 0, 1), PURE(Float64Ceil, 1, 0, 1),
206     PURE(Float64RoundTruncate, 1, 0, 1), PURE(Float64RoundTiesAway, 1, 0, 1)
207 #undef PURE
208 };
209
210
211 typedef MachineOperatorTestWithParam<PureOperator> MachinePureOperatorTest;
212
213 }  // namespace
214
215
216 TEST_P(MachinePureOperatorTest, InstancesAreGloballyShared) {
217   const PureOperator& pop = GetParam();
218   MachineOperatorBuilder machine1(type());
219   MachineOperatorBuilder machine2(type());
220   EXPECT_EQ((machine1.*pop.constructor)(), (machine2.*pop.constructor)());
221 }
222
223
224 TEST_P(MachinePureOperatorTest, NumberOfInputsAndOutputs) {
225   MachineOperatorBuilder machine(type());
226   const PureOperator& pop = GetParam();
227   const Operator* op = (machine.*pop.constructor)();
228
229   EXPECT_EQ(pop.value_input_count, op->ValueInputCount());
230   EXPECT_EQ(0, op->EffectInputCount());
231   EXPECT_EQ(pop.control_input_count, op->ControlInputCount());
232   EXPECT_EQ(pop.value_input_count + pop.control_input_count,
233             OperatorProperties::GetTotalInputCount(op));
234
235   EXPECT_EQ(pop.value_output_count, op->ValueOutputCount());
236   EXPECT_EQ(0, op->EffectOutputCount());
237   EXPECT_EQ(0, op->ControlOutputCount());
238 }
239
240
241 TEST_P(MachinePureOperatorTest, MarkedAsPure) {
242   MachineOperatorBuilder machine(type());
243   const PureOperator& pop = GetParam();
244   const Operator* op = (machine.*pop.constructor)();
245   EXPECT_TRUE(op->HasProperty(Operator::kPure));
246 }
247
248
249 TEST_P(MachinePureOperatorTest, OpcodeIsCorrect) {
250   MachineOperatorBuilder machine(type());
251   const PureOperator& pop = GetParam();
252   const Operator* op = (machine.*pop.constructor)();
253   EXPECT_EQ(pop.opcode, op->opcode());
254 }
255
256
257 INSTANTIATE_TEST_CASE_P(
258     MachineOperatorTest, MachinePureOperatorTest,
259     ::testing::Combine(::testing::ValuesIn(kMachineReps),
260                        ::testing::ValuesIn(kPureOperators)));
261
262 #endif  // GTEST_HAS_COMBINE
263
264
265 // -----------------------------------------------------------------------------
266 // Pseudo operators.
267
268
269 TEST(MachineOperatorTest, PseudoOperatorsWhenWordSizeIs32Bit) {
270   MachineOperatorBuilder machine(kRepWord32);
271   EXPECT_EQ(machine.Word32And(), machine.WordAnd());
272   EXPECT_EQ(machine.Word32Or(), machine.WordOr());
273   EXPECT_EQ(machine.Word32Xor(), machine.WordXor());
274   EXPECT_EQ(machine.Word32Shl(), machine.WordShl());
275   EXPECT_EQ(machine.Word32Shr(), machine.WordShr());
276   EXPECT_EQ(machine.Word32Sar(), machine.WordSar());
277   EXPECT_EQ(machine.Word32Ror(), machine.WordRor());
278   EXPECT_EQ(machine.Word32Equal(), machine.WordEqual());
279   EXPECT_EQ(machine.Int32Add(), machine.IntAdd());
280   EXPECT_EQ(machine.Int32Sub(), machine.IntSub());
281   EXPECT_EQ(machine.Int32Mul(), machine.IntMul());
282   EXPECT_EQ(machine.Int32Div(), machine.IntDiv());
283   EXPECT_EQ(machine.Uint32Div(), machine.UintDiv());
284   EXPECT_EQ(machine.Int32Mod(), machine.IntMod());
285   EXPECT_EQ(machine.Uint32Mod(), machine.UintMod());
286   EXPECT_EQ(machine.Int32LessThan(), machine.IntLessThan());
287   EXPECT_EQ(machine.Int32LessThanOrEqual(), machine.IntLessThanOrEqual());
288 }
289
290
291 TEST(MachineOperatorTest, PseudoOperatorsWhenWordSizeIs64Bit) {
292   MachineOperatorBuilder machine(kRepWord64);
293   EXPECT_EQ(machine.Word64And(), machine.WordAnd());
294   EXPECT_EQ(machine.Word64Or(), machine.WordOr());
295   EXPECT_EQ(machine.Word64Xor(), machine.WordXor());
296   EXPECT_EQ(machine.Word64Shl(), machine.WordShl());
297   EXPECT_EQ(machine.Word64Shr(), machine.WordShr());
298   EXPECT_EQ(machine.Word64Sar(), machine.WordSar());
299   EXPECT_EQ(machine.Word64Ror(), machine.WordRor());
300   EXPECT_EQ(machine.Word64Equal(), machine.WordEqual());
301   EXPECT_EQ(machine.Int64Add(), machine.IntAdd());
302   EXPECT_EQ(machine.Int64Sub(), machine.IntSub());
303   EXPECT_EQ(machine.Int64Mul(), machine.IntMul());
304   EXPECT_EQ(machine.Int64Div(), machine.IntDiv());
305   EXPECT_EQ(machine.Uint64Div(), machine.UintDiv());
306   EXPECT_EQ(machine.Int64Mod(), machine.IntMod());
307   EXPECT_EQ(machine.Uint64Mod(), machine.UintMod());
308   EXPECT_EQ(machine.Int64LessThan(), machine.IntLessThan());
309   EXPECT_EQ(machine.Int64LessThanOrEqual(), machine.IntLessThanOrEqual());
310 }
311
312 }  // namespace compiler
313 }  // namespace internal
314 }  // namespace v8