Upstream version 11.39.266.0
[platform/framework/web/crosswalk.git] / src / v8 / src / compiler / machine-operator-reducer-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/base/bits.h"
6 #include "src/compiler/graph-unittest.h"
7 #include "src/compiler/js-graph.h"
8 #include "src/compiler/machine-operator-reducer.h"
9 #include "src/compiler/typer.h"
10
11 namespace v8 {
12 namespace internal {
13 namespace compiler {
14
15 class MachineOperatorReducerTest : public GraphTest {
16  public:
17   explicit MachineOperatorReducerTest(int num_parameters = 2)
18       : GraphTest(num_parameters) {}
19
20  protected:
21   Reduction Reduce(Node* node) {
22     Typer typer(zone());
23     JSOperatorBuilder javascript(zone());
24     JSGraph jsgraph(graph(), common(), &javascript, &typer, &machine_);
25     MachineOperatorReducer reducer(&jsgraph);
26     return reducer.Reduce(node);
27   }
28
29   MachineOperatorBuilder* machine() { return &machine_; }
30
31  private:
32   MachineOperatorBuilder machine_;
33 };
34
35
36 template <typename T>
37 class MachineOperatorReducerTestWithParam
38     : public MachineOperatorReducerTest,
39       public ::testing::WithParamInterface<T> {
40  public:
41   explicit MachineOperatorReducerTestWithParam(int num_parameters = 2)
42       : MachineOperatorReducerTest(num_parameters) {}
43   virtual ~MachineOperatorReducerTestWithParam() {}
44 };
45
46
47 namespace {
48
49 static const float kFloat32Values[] = {
50     -std::numeric_limits<float>::infinity(), -2.70497e+38f, -1.4698e+37f,
51     -1.22813e+35f,                           -1.20555e+35f, -1.34584e+34f,
52     -1.0079e+32f,                            -6.49364e+26f, -3.06077e+25f,
53     -1.46821e+25f,                           -1.17658e+23f, -1.9617e+22f,
54     -2.7357e+20f,                            -1.48708e+13f, -1.89633e+12f,
55     -4.66622e+11f,                           -2.22581e+11f, -1.45381e+10f,
56     -1.3956e+09f,                            -1.32951e+09f, -1.30721e+09f,
57     -1.19756e+09f,                           -9.26822e+08f, -6.35647e+08f,
58     -4.00037e+08f,                           -1.81227e+08f, -5.09256e+07f,
59     -964300.0f,                              -192446.0f,    -28455.0f,
60     -27194.0f,                               -26401.0f,     -20575.0f,
61     -17069.0f,                               -9167.0f,      -960.178f,
62     -113.0f,                                 -62.0f,        -15.0f,
63     -7.0f,                                   -0.0256635f,   -4.60374e-07f,
64     -3.63759e-10f,                           -4.30175e-14f, -5.27385e-15f,
65     -1.48084e-15f,                           -1.05755e-19f, -3.2995e-21f,
66     -1.67354e-23f,                           -1.11885e-23f, -1.78506e-30f,
67     -5.07594e-31f,                           -3.65799e-31f, -1.43718e-34f,
68     -1.27126e-38f,                           -0.0f,         0.0f,
69     1.17549e-38f,                            1.56657e-37f,  4.08512e-29f,
70     3.31357e-28f,                            6.25073e-22f,  4.1723e-13f,
71     1.44343e-09f,                            5.27004e-08f,  9.48298e-08f,
72     5.57888e-07f,                            4.89988e-05f,  0.244326f,
73     12.4895f,                                19.0f,         47.0f,
74     106.0f,                                  538.324f,      564.536f,
75     819.124f,                                7048.0f,       12611.0f,
76     19878.0f,                                20309.0f,      797056.0f,
77     1.77219e+09f,                            1.51116e+11f,  4.18193e+13f,
78     3.59167e+16f,                            3.38211e+19f,  2.67488e+20f,
79     1.78831e+21f,                            9.20914e+21f,  8.35654e+23f,
80     1.4495e+24f,                             5.94015e+25f,  4.43608e+30f,
81     2.44502e+33f,                            2.61152e+33f,  1.38178e+37f,
82     1.71306e+37f,                            3.31899e+38f,  3.40282e+38f,
83     std::numeric_limits<float>::infinity()};
84
85
86 static const double kFloat64Values[] = {
87     -V8_INFINITY,  -4.23878e+275, -5.82632e+265, -6.60355e+220, -6.26172e+212,
88     -2.56222e+211, -4.82408e+201, -1.84106e+157, -1.63662e+127, -1.55772e+100,
89     -1.67813e+72,  -2.3382e+55,   -3.179e+30,    -1.441e+09,    -1.0647e+09,
90     -7.99361e+08,  -5.77375e+08,  -2.20984e+08,  -32757,        -13171,
91     -9970,         -3984,         -107,          -105,          -92,
92     -77,           -61,           -0.000208163,  -1.86685e-06,  -1.17296e-10,
93     -9.26358e-11,  -5.08004e-60,  -1.74753e-65,  -1.06561e-71,  -5.67879e-79,
94     -5.78459e-130, -2.90989e-171, -7.15489e-243, -3.76242e-252, -1.05639e-263,
95     -4.40497e-267, -2.19666e-273, -4.9998e-276,  -5.59821e-278, -2.03855e-282,
96     -5.99335e-283, -7.17554e-284, -3.11744e-309, -0.0,          0.0,
97     2.22507e-308,  1.30127e-270,  7.62898e-260,  4.00313e-249,  3.16829e-233,
98     1.85244e-228,  2.03544e-129,  1.35126e-110,  1.01182e-106,  5.26333e-94,
99     1.35292e-90,   2.85394e-83,   1.78323e-77,   5.4967e-57,    1.03207e-25,
100     4.57401e-25,   1.58738e-05,   2,             125,           2310,
101     9636,          14802,         17168,         28945,         29305,
102     4.81336e+07,   1.41207e+08,   4.65962e+08,   1.40499e+09,   2.12648e+09,
103     8.80006e+30,   1.4446e+45,    1.12164e+54,   2.48188e+89,   6.71121e+102,
104     3.074e+112,    4.9699e+152,   5.58383e+166,  4.30654e+172,  7.08824e+185,
105     9.6586e+214,   2.028e+223,    6.63277e+243,  1.56192e+261,  1.23202e+269,
106     5.72883e+289,  8.5798e+290,   1.40256e+294,  1.79769e+308,  V8_INFINITY};
107
108
109 static const int32_t kInt32Values[] = {
110     -2147483647 - 1, -1914954528, -1698749618, -1578693386, -1577976073,
111     -1573998034,     -1529085059, -1499540537, -1299205097, -1090814845,
112     -938186388,      -806828902,  -750927650,  -520676892,  -513661538,
113     -453036354,      -433622833,  -282638793,  -28375,      -27788,
114     -22770,          -18806,      -14173,      -11956,      -11200,
115     -10212,          -8160,       -3751,       -2758,       -1522,
116     -121,            -120,        -118,        -117,        -106,
117     -84,             -80,         -74,         -59,         -52,
118     -48,             -39,         -35,         -17,         -11,
119     -10,             -9,          -7,          -5,          0,
120     9,               12,          17,          23,          29,
121     31,              33,          35,          40,          47,
122     55,              56,          62,          64,          67,
123     68,              69,          74,          79,          84,
124     89,              90,          97,          104,         118,
125     124,             126,         127,         7278,        17787,
126     24136,           24202,       25570,       26680,       30242,
127     32399,           420886487,   642166225,   821912648,   822577803,
128     851385718,       1212241078,  1411419304,  1589626102,  1596437184,
129     1876245816,      1954730266,  2008792749,  2045320228,  2147483647};
130
131
132 static const int64_t kInt64Values[] = {
133     V8_INT64_C(-9223372036854775807) - 1, V8_INT64_C(-8974392461363618006),
134     V8_INT64_C(-8874367046689588135),     V8_INT64_C(-8269197512118230839),
135     V8_INT64_C(-8146091527100606733),     V8_INT64_C(-7550917981466150848),
136     V8_INT64_C(-7216590251577894337),     V8_INT64_C(-6464086891160048440),
137     V8_INT64_C(-6365616494908257190),     V8_INT64_C(-6305630541365849726),
138     V8_INT64_C(-5982222642272245453),     V8_INT64_C(-5510103099058504169),
139     V8_INT64_C(-5496838675802432701),     V8_INT64_C(-4047626578868642657),
140     V8_INT64_C(-4033755046900164544),     V8_INT64_C(-3554299241457877041),
141     V8_INT64_C(-2482258764588614470),     V8_INT64_C(-1688515425526875335),
142     V8_INT64_C(-924784137176548532),      V8_INT64_C(-725316567157391307),
143     V8_INT64_C(-439022654781092241),      V8_INT64_C(-105545757668917080),
144     V8_INT64_C(-2088319373),              V8_INT64_C(-2073699916),
145     V8_INT64_C(-1844949911),              V8_INT64_C(-1831090548),
146     V8_INT64_C(-1756711933),              V8_INT64_C(-1559409497),
147     V8_INT64_C(-1281179700),              V8_INT64_C(-1211513985),
148     V8_INT64_C(-1182371520),              V8_INT64_C(-785934753),
149     V8_INT64_C(-767480697),               V8_INT64_C(-705745662),
150     V8_INT64_C(-514362436),               V8_INT64_C(-459916580),
151     V8_INT64_C(-312328082),               V8_INT64_C(-302949707),
152     V8_INT64_C(-285499304),               V8_INT64_C(-125701262),
153     V8_INT64_C(-95139843),                V8_INT64_C(-32768),
154     V8_INT64_C(-27542),                   V8_INT64_C(-23600),
155     V8_INT64_C(-18582),                   V8_INT64_C(-17770),
156     V8_INT64_C(-9086),                    V8_INT64_C(-9010),
157     V8_INT64_C(-8244),                    V8_INT64_C(-2890),
158     V8_INT64_C(-103),                     V8_INT64_C(-34),
159     V8_INT64_C(-27),                      V8_INT64_C(-25),
160     V8_INT64_C(-9),                       V8_INT64_C(-7),
161     V8_INT64_C(0),                        V8_INT64_C(2),
162     V8_INT64_C(38),                       V8_INT64_C(58),
163     V8_INT64_C(65),                       V8_INT64_C(93),
164     V8_INT64_C(111),                      V8_INT64_C(1003),
165     V8_INT64_C(1267),                     V8_INT64_C(12797),
166     V8_INT64_C(23122),                    V8_INT64_C(28200),
167     V8_INT64_C(30888),                    V8_INT64_C(42648848),
168     V8_INT64_C(116836693),                V8_INT64_C(263003643),
169     V8_INT64_C(571039860),                V8_INT64_C(1079398689),
170     V8_INT64_C(1145196402),               V8_INT64_C(1184846321),
171     V8_INT64_C(1758281648),               V8_INT64_C(1859991374),
172     V8_INT64_C(1960251588),               V8_INT64_C(2042443199),
173     V8_INT64_C(296220586027987448),       V8_INT64_C(1015494173071134726),
174     V8_INT64_C(1151237951914455318),      V8_INT64_C(1331941174616854174),
175     V8_INT64_C(2022020418667972654),      V8_INT64_C(2450251424374977035),
176     V8_INT64_C(3668393562685561486),      V8_INT64_C(4858229301215502171),
177     V8_INT64_C(4919426235170669383),      V8_INT64_C(5034286595330341762),
178     V8_INT64_C(5055797915536941182),      V8_INT64_C(6072389716149252074),
179     V8_INT64_C(6185309910199801210),      V8_INT64_C(6297328311011094138),
180     V8_INT64_C(6932372858072165827),      V8_INT64_C(8483640924987737210),
181     V8_INT64_C(8663764179455849203),      V8_INT64_C(8877197042645298254),
182     V8_INT64_C(8901543506779157333),      V8_INT64_C(9223372036854775807)};
183
184
185 static const uint32_t kUint32Values[] = {
186     0x00000000, 0x00000001, 0xffffffff, 0x1b09788b, 0x04c5fce8, 0xcc0de5bf,
187     0x273a798e, 0x187937a3, 0xece3af83, 0x5495a16b, 0x0b668ecc, 0x11223344,
188     0x0000009e, 0x00000043, 0x0000af73, 0x0000116b, 0x00658ecc, 0x002b3b4c,
189     0x88776655, 0x70000000, 0x07200000, 0x7fffffff, 0x56123761, 0x7fffff00,
190     0x761c4761, 0x80000000, 0x88888888, 0xa0000000, 0xdddddddd, 0xe0000000,
191     0xeeeeeeee, 0xfffffffd, 0xf0000000, 0x007fffff, 0x003fffff, 0x001fffff,
192     0x000fffff, 0x0007ffff, 0x0003ffff, 0x0001ffff, 0x0000ffff, 0x00007fff,
193     0x00003fff, 0x00001fff, 0x00000fff, 0x000007ff, 0x000003ff, 0x000001ff};
194
195 }  // namespace
196
197
198 // -----------------------------------------------------------------------------
199 // Unary operators
200
201
202 namespace {
203
204 struct UnaryOperator {
205   const Operator* (MachineOperatorBuilder::*constructor)();
206   const char* constructor_name;
207 };
208
209
210 std::ostream& operator<<(std::ostream& os, const UnaryOperator& unop) {
211   return os << unop.constructor_name;
212 }
213
214
215 static const UnaryOperator kUnaryOperators[] = {
216     {&MachineOperatorBuilder::ChangeInt32ToFloat64, "ChangeInt32ToFloat64"},
217     {&MachineOperatorBuilder::ChangeUint32ToFloat64, "ChangeUint32ToFloat64"},
218     {&MachineOperatorBuilder::ChangeFloat64ToInt32, "ChangeFloat64ToInt32"},
219     {&MachineOperatorBuilder::ChangeFloat64ToUint32, "ChangeFloat64ToUint32"},
220     {&MachineOperatorBuilder::ChangeInt32ToInt64, "ChangeInt32ToInt64"},
221     {&MachineOperatorBuilder::ChangeUint32ToUint64, "ChangeUint32ToUint64"},
222     {&MachineOperatorBuilder::TruncateFloat64ToInt32, "TruncateFloat64ToInt32"},
223     {&MachineOperatorBuilder::TruncateInt64ToInt32, "TruncateInt64ToInt32"}};
224
225 }  // namespace
226
227
228 typedef MachineOperatorReducerTestWithParam<UnaryOperator>
229     MachineUnaryOperatorReducerTest;
230
231
232 TEST_P(MachineUnaryOperatorReducerTest, Parameter) {
233   const UnaryOperator unop = GetParam();
234   Reduction reduction =
235       Reduce(graph()->NewNode((machine()->*unop.constructor)(), Parameter(0)));
236   EXPECT_FALSE(reduction.Changed());
237 }
238
239
240 INSTANTIATE_TEST_CASE_P(MachineOperatorReducerTest,
241                         MachineUnaryOperatorReducerTest,
242                         ::testing::ValuesIn(kUnaryOperators));
243
244
245 // -----------------------------------------------------------------------------
246 // ChangeFloat64ToFloat32
247
248
249 TEST_F(MachineOperatorReducerTest, ChangeFloat64ToFloat32WithConstant) {
250   TRACED_FOREACH(float, x, kFloat32Values) {
251     Reduction reduction = Reduce(graph()->NewNode(
252         machine()->ChangeFloat32ToFloat64(), Float32Constant(x)));
253     ASSERT_TRUE(reduction.Changed());
254     EXPECT_THAT(reduction.replacement(), IsFloat64Constant(x));
255   }
256 }
257
258
259 // -----------------------------------------------------------------------------
260 // ChangeFloat64ToInt32
261
262
263 TEST_F(MachineOperatorReducerTest,
264        ChangeFloat64ToInt32WithChangeInt32ToFloat64) {
265   Node* value = Parameter(0);
266   Reduction reduction = Reduce(graph()->NewNode(
267       machine()->ChangeFloat64ToInt32(),
268       graph()->NewNode(machine()->ChangeInt32ToFloat64(), value)));
269   ASSERT_TRUE(reduction.Changed());
270   EXPECT_EQ(value, reduction.replacement());
271 }
272
273
274 TEST_F(MachineOperatorReducerTest, ChangeFloat64ToInt32WithConstant) {
275   TRACED_FOREACH(int32_t, x, kInt32Values) {
276     Reduction reduction = Reduce(graph()->NewNode(
277         machine()->ChangeFloat64ToInt32(), Float64Constant(FastI2D(x))));
278     ASSERT_TRUE(reduction.Changed());
279     EXPECT_THAT(reduction.replacement(), IsInt32Constant(x));
280   }
281 }
282
283
284 // -----------------------------------------------------------------------------
285 // ChangeFloat64ToUint32
286
287
288 TEST_F(MachineOperatorReducerTest,
289        ChangeFloat64ToUint32WithChangeUint32ToFloat64) {
290   Node* value = Parameter(0);
291   Reduction reduction = Reduce(graph()->NewNode(
292       machine()->ChangeFloat64ToUint32(),
293       graph()->NewNode(machine()->ChangeUint32ToFloat64(), value)));
294   ASSERT_TRUE(reduction.Changed());
295   EXPECT_EQ(value, reduction.replacement());
296 }
297
298
299 TEST_F(MachineOperatorReducerTest, ChangeFloat64ToUint32WithConstant) {
300   TRACED_FOREACH(uint32_t, x, kUint32Values) {
301     Reduction reduction = Reduce(graph()->NewNode(
302         machine()->ChangeFloat64ToUint32(), Float64Constant(FastUI2D(x))));
303     ASSERT_TRUE(reduction.Changed());
304     EXPECT_THAT(reduction.replacement(), IsInt32Constant(bit_cast<int32_t>(x)));
305   }
306 }
307
308
309 // -----------------------------------------------------------------------------
310 // ChangeInt32ToFloat64
311
312
313 TEST_F(MachineOperatorReducerTest, ChangeInt32ToFloat64WithConstant) {
314   TRACED_FOREACH(int32_t, x, kInt32Values) {
315     Reduction reduction = Reduce(
316         graph()->NewNode(machine()->ChangeInt32ToFloat64(), Int32Constant(x)));
317     ASSERT_TRUE(reduction.Changed());
318     EXPECT_THAT(reduction.replacement(), IsFloat64Constant(FastI2D(x)));
319   }
320 }
321
322
323 // -----------------------------------------------------------------------------
324 // ChangeInt32ToInt64
325
326
327 TEST_F(MachineOperatorReducerTest, ChangeInt32ToInt64WithConstant) {
328   TRACED_FOREACH(int32_t, x, kInt32Values) {
329     Reduction reduction = Reduce(
330         graph()->NewNode(machine()->ChangeInt32ToInt64(), Int32Constant(x)));
331     ASSERT_TRUE(reduction.Changed());
332     EXPECT_THAT(reduction.replacement(), IsInt64Constant(x));
333   }
334 }
335
336
337 // -----------------------------------------------------------------------------
338 // ChangeUint32ToFloat64
339
340
341 TEST_F(MachineOperatorReducerTest, ChangeUint32ToFloat64WithConstant) {
342   TRACED_FOREACH(uint32_t, x, kUint32Values) {
343     Reduction reduction =
344         Reduce(graph()->NewNode(machine()->ChangeUint32ToFloat64(),
345                                 Int32Constant(bit_cast<int32_t>(x))));
346     ASSERT_TRUE(reduction.Changed());
347     EXPECT_THAT(reduction.replacement(), IsFloat64Constant(FastUI2D(x)));
348   }
349 }
350
351
352 // -----------------------------------------------------------------------------
353 // ChangeUint32ToUint64
354
355
356 TEST_F(MachineOperatorReducerTest, ChangeUint32ToUint64WithConstant) {
357   TRACED_FOREACH(uint32_t, x, kUint32Values) {
358     Reduction reduction =
359         Reduce(graph()->NewNode(machine()->ChangeUint32ToUint64(),
360                                 Int32Constant(bit_cast<int32_t>(x))));
361     ASSERT_TRUE(reduction.Changed());
362     EXPECT_THAT(reduction.replacement(),
363                 IsInt64Constant(bit_cast<int64_t>(static_cast<uint64_t>(x))));
364   }
365 }
366
367
368 // -----------------------------------------------------------------------------
369 // TruncateFloat64ToFloat32
370
371
372 TEST_F(MachineOperatorReducerTest,
373        TruncateFloat64ToFloat32WithChangeFloat32ToFloat64) {
374   Node* value = Parameter(0);
375   Reduction reduction = Reduce(graph()->NewNode(
376       machine()->TruncateFloat64ToFloat32(),
377       graph()->NewNode(machine()->ChangeFloat32ToFloat64(), value)));
378   ASSERT_TRUE(reduction.Changed());
379   EXPECT_EQ(value, reduction.replacement());
380 }
381
382
383 TEST_F(MachineOperatorReducerTest, TruncateFloat64ToFloat32WithConstant) {
384   TRACED_FOREACH(double, x, kFloat64Values) {
385     Reduction reduction = Reduce(graph()->NewNode(
386         machine()->TruncateFloat64ToFloat32(), Float64Constant(x)));
387     ASSERT_TRUE(reduction.Changed());
388     EXPECT_THAT(reduction.replacement(), IsFloat32Constant(DoubleToFloat32(x)));
389   }
390 }
391
392
393 // -----------------------------------------------------------------------------
394 // TruncateFloat64ToInt32
395
396
397 TEST_F(MachineOperatorReducerTest,
398        TruncateFloat64ToInt32WithChangeInt32ToFloat64) {
399   Node* value = Parameter(0);
400   Reduction reduction = Reduce(graph()->NewNode(
401       machine()->TruncateFloat64ToInt32(),
402       graph()->NewNode(machine()->ChangeInt32ToFloat64(), value)));
403   ASSERT_TRUE(reduction.Changed());
404   EXPECT_EQ(value, reduction.replacement());
405 }
406
407
408 TEST_F(MachineOperatorReducerTest, TruncateFloat64ToInt32WithConstant) {
409   TRACED_FOREACH(double, x, kFloat64Values) {
410     Reduction reduction = Reduce(graph()->NewNode(
411         machine()->TruncateFloat64ToInt32(), Float64Constant(x)));
412     ASSERT_TRUE(reduction.Changed());
413     EXPECT_THAT(reduction.replacement(), IsInt32Constant(DoubleToInt32(x)));
414   }
415 }
416
417
418 // -----------------------------------------------------------------------------
419 // TruncateInt64ToInt32
420
421
422 TEST_F(MachineOperatorReducerTest, TruncateInt64ToInt32WithChangeInt32ToInt64) {
423   Node* value = Parameter(0);
424   Reduction reduction = Reduce(graph()->NewNode(
425       machine()->TruncateInt64ToInt32(),
426       graph()->NewNode(machine()->ChangeInt32ToInt64(), value)));
427   ASSERT_TRUE(reduction.Changed());
428   EXPECT_EQ(value, reduction.replacement());
429 }
430
431
432 TEST_F(MachineOperatorReducerTest, TruncateInt64ToInt32WithConstant) {
433   TRACED_FOREACH(int64_t, x, kInt64Values) {
434     Reduction reduction = Reduce(
435         graph()->NewNode(machine()->TruncateInt64ToInt32(), Int64Constant(x)));
436     ASSERT_TRUE(reduction.Changed());
437     EXPECT_THAT(reduction.replacement(),
438                 IsInt32Constant(bit_cast<int32_t>(
439                     static_cast<uint32_t>(bit_cast<uint64_t>(x)))));
440   }
441 }
442
443
444 // -----------------------------------------------------------------------------
445 // Word32Ror
446
447
448 TEST_F(MachineOperatorReducerTest, ReduceToWord32RorWithParameters) {
449   Node* value = Parameter(0);
450   Node* shift = Parameter(1);
451   Node* shl = graph()->NewNode(machine()->Word32Shl(), value, shift);
452   Node* shr = graph()->NewNode(
453       machine()->Word32Shr(), value,
454       graph()->NewNode(machine()->Int32Sub(), Int32Constant(32), shift));
455
456   // (x << y) | (x >> (32 - y)) => x ror y
457   Node* node1 = graph()->NewNode(machine()->Word32Or(), shl, shr);
458   Reduction reduction1 = Reduce(node1);
459   EXPECT_TRUE(reduction1.Changed());
460   EXPECT_EQ(reduction1.replacement(), node1);
461   EXPECT_THAT(reduction1.replacement(), IsWord32Ror(value, shift));
462
463   // (x >> (32 - y)) | (x << y) => x ror y
464   Node* node2 = graph()->NewNode(machine()->Word32Or(), shr, shl);
465   Reduction reduction2 = Reduce(node2);
466   EXPECT_TRUE(reduction2.Changed());
467   EXPECT_EQ(reduction2.replacement(), node2);
468   EXPECT_THAT(reduction2.replacement(), IsWord32Ror(value, shift));
469 }
470
471
472 TEST_F(MachineOperatorReducerTest, ReduceToWord32RorWithConstant) {
473   Node* value = Parameter(0);
474   TRACED_FORRANGE(int32_t, k, 0, 31) {
475     Node* shl =
476         graph()->NewNode(machine()->Word32Shl(), value, Int32Constant(k));
477     Node* shr =
478         graph()->NewNode(machine()->Word32Shr(), value, Int32Constant(32 - k));
479
480     // (x << K) | (x >> ((32 - K) - y)) => x ror K
481     Node* node1 = graph()->NewNode(machine()->Word32Or(), shl, shr);
482     Reduction reduction1 = Reduce(node1);
483     EXPECT_TRUE(reduction1.Changed());
484     EXPECT_EQ(reduction1.replacement(), node1);
485     EXPECT_THAT(reduction1.replacement(),
486                 IsWord32Ror(value, IsInt32Constant(k)));
487
488     // (x >> (32 - K)) | (x << K) => x ror K
489     Node* node2 = graph()->NewNode(machine()->Word32Or(), shr, shl);
490     Reduction reduction2 = Reduce(node2);
491     EXPECT_TRUE(reduction2.Changed());
492     EXPECT_EQ(reduction2.replacement(), node2);
493     EXPECT_THAT(reduction2.replacement(),
494                 IsWord32Ror(value, IsInt32Constant(k)));
495   }
496 }
497
498
499 TEST_F(MachineOperatorReducerTest, Word32RorWithZeroShift) {
500   Node* value = Parameter(0);
501   Node* node =
502       graph()->NewNode(machine()->Word32Ror(), value, Int32Constant(0));
503   Reduction reduction = Reduce(node);
504   EXPECT_TRUE(reduction.Changed());
505   EXPECT_EQ(reduction.replacement(), value);
506 }
507
508
509 TEST_F(MachineOperatorReducerTest, Word32RorWithConstants) {
510   TRACED_FOREACH(int32_t, x, kUint32Values) {
511     TRACED_FORRANGE(int32_t, y, 0, 31) {
512       Node* node = graph()->NewNode(machine()->Word32Ror(), Int32Constant(x),
513                                     Int32Constant(y));
514       Reduction reduction = Reduce(node);
515       EXPECT_TRUE(reduction.Changed());
516       EXPECT_THAT(reduction.replacement(),
517                   IsInt32Constant(base::bits::RotateRight32(x, y)));
518     }
519   }
520 }
521
522
523 // -----------------------------------------------------------------------------
524 // Int32AddWithOverflow
525
526
527 TEST_F(MachineOperatorReducerTest, Int32AddWithOverflowWithZero) {
528   Node* p0 = Parameter(0);
529   {
530     Node* add = graph()->NewNode(machine()->Int32AddWithOverflow(),
531                                  Int32Constant(0), p0);
532
533     Reduction r = Reduce(graph()->NewNode(common()->Projection(1), add));
534     ASSERT_TRUE(r.Changed());
535     EXPECT_THAT(r.replacement(), IsInt32Constant(0));
536
537     r = Reduce(graph()->NewNode(common()->Projection(0), add));
538     ASSERT_TRUE(r.Changed());
539     EXPECT_EQ(p0, r.replacement());
540   }
541   {
542     Node* add = graph()->NewNode(machine()->Int32AddWithOverflow(), p0,
543                                  Int32Constant(0));
544
545     Reduction r = Reduce(graph()->NewNode(common()->Projection(1), add));
546     ASSERT_TRUE(r.Changed());
547     EXPECT_THAT(r.replacement(), IsInt32Constant(0));
548
549     r = Reduce(graph()->NewNode(common()->Projection(0), add));
550     ASSERT_TRUE(r.Changed());
551     EXPECT_EQ(p0, r.replacement());
552   }
553 }
554
555
556 TEST_F(MachineOperatorReducerTest, Int32AddWithOverflowWithConstant) {
557   TRACED_FOREACH(int32_t, x, kInt32Values) {
558     TRACED_FOREACH(int32_t, y, kInt32Values) {
559       int32_t z;
560       Node* add = graph()->NewNode(machine()->Int32AddWithOverflow(),
561                                    Int32Constant(x), Int32Constant(y));
562
563       Reduction r = Reduce(graph()->NewNode(common()->Projection(1), add));
564       ASSERT_TRUE(r.Changed());
565       EXPECT_THAT(r.replacement(),
566                   IsInt32Constant(base::bits::SignedAddOverflow32(x, y, &z)));
567
568       r = Reduce(graph()->NewNode(common()->Projection(0), add));
569       ASSERT_TRUE(r.Changed());
570       EXPECT_THAT(r.replacement(), IsInt32Constant(z));
571     }
572   }
573 }
574
575
576 // -----------------------------------------------------------------------------
577 // Int32SubWithOverflow
578
579
580 TEST_F(MachineOperatorReducerTest, Int32SubWithOverflowWithZero) {
581   Node* p0 = Parameter(0);
582   Node* add =
583       graph()->NewNode(machine()->Int32SubWithOverflow(), p0, Int32Constant(0));
584
585   Reduction r = Reduce(graph()->NewNode(common()->Projection(1), add));
586   ASSERT_TRUE(r.Changed());
587   EXPECT_THAT(r.replacement(), IsInt32Constant(0));
588
589   r = Reduce(graph()->NewNode(common()->Projection(0), add));
590   ASSERT_TRUE(r.Changed());
591   EXPECT_EQ(p0, r.replacement());
592 }
593
594
595 TEST_F(MachineOperatorReducerTest, Int32SubWithOverflowWithConstant) {
596   TRACED_FOREACH(int32_t, x, kInt32Values) {
597     TRACED_FOREACH(int32_t, y, kInt32Values) {
598       int32_t z;
599       Node* add = graph()->NewNode(machine()->Int32SubWithOverflow(),
600                                    Int32Constant(x), Int32Constant(y));
601
602       Reduction r = Reduce(graph()->NewNode(common()->Projection(1), add));
603       ASSERT_TRUE(r.Changed());
604       EXPECT_THAT(r.replacement(),
605                   IsInt32Constant(base::bits::SignedSubOverflow32(x, y, &z)));
606
607       r = Reduce(graph()->NewNode(common()->Projection(0), add));
608       ASSERT_TRUE(r.Changed());
609       EXPECT_THAT(r.replacement(), IsInt32Constant(z));
610     }
611   }
612 }
613
614 }  // namespace compiler
615 }  // namespace internal
616 }  // namespace v8