| OLD | NEW | 
|---|
| 1 // Copyright 2014 the V8 project authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be | 
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. | 
| 4 | 4 | 
| 5 #include <limits> | 5 #include <limits> | 
| 6 | 6 | 
| 7 #include "src/v8.h" | 7 #include "src/v8.h" | 
| 8 #include "test/cctest/cctest.h" | 8 #include "test/cctest/cctest.h" | 
| 9 #include "test/cctest/compiler/graph-builder-tester.h" | 9 #include "test/cctest/compiler/graph-builder-tester.h" | 
| 10 #include "test/cctest/compiler/value-helper.h" | 10 #include "test/cctest/compiler/value-helper.h" | 
| (...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 72     CHECK_EQ(expected, *m.Value().handle()); | 72     CHECK_EQ(expected, *m.Value().handle()); | 
| 73   } | 73   } | 
| 74 | 74 | 
| 75   void CheckNumberConstant(Node* n, double expected) { | 75   void CheckNumberConstant(Node* n, double expected) { | 
| 76     NumberMatcher m(n); | 76     NumberMatcher m(n); | 
| 77     CHECK_EQ(IrOpcode::kNumberConstant, n->opcode()); | 77     CHECK_EQ(IrOpcode::kNumberConstant, n->opcode()); | 
| 78     CHECK(m.HasValue()); | 78     CHECK(m.HasValue()); | 
| 79     CHECK_EQ(expected, m.Value()); | 79     CHECK_EQ(expected, m.Value()); | 
| 80   } | 80   } | 
| 81 | 81 | 
| 82   Node* Parameter(Type* type, int index = 0) { | 82   Node* Parameter(int index = 0) { | 
| 83     Node* node = graph()->NewNode(common()->Parameter(index), graph()->start()); | 83     return graph()->NewNode(common()->Parameter(index), graph()->start()); | 
| 84     NodeProperties::SetBounds(node, Bounds(type)); |  | 
| 85     return node; |  | 
| 86   } | 84   } | 
| 87 | 85 | 
| 88   Node* Parameter(int index = 0) { return Parameter(Type::Any(), index); } |  | 
| 89 |  | 
| 90   void CheckTypeError(MachineTypeUnion from, MachineTypeUnion to) { | 86   void CheckTypeError(MachineTypeUnion from, MachineTypeUnion to) { | 
| 91     changer()->testing_type_errors_ = true; | 87     changer()->testing_type_errors_ = true; | 
| 92     changer()->type_error_ = false; | 88     changer()->type_error_ = false; | 
| 93     Node* n = Parameter(0); | 89     Node* n = Parameter(0); | 
| 94     Node* c = changer()->GetRepresentationFor(n, from, to); | 90     Node* c = changer()->GetRepresentationFor(n, from, to); | 
| 95     CHECK(changer()->type_error_); | 91     CHECK(changer()->type_error_); | 
| 96     CHECK_EQ(n, c); | 92     CHECK_EQ(n, c); | 
| 97   } | 93   } | 
| 98 | 94 | 
| 99   void CheckNop(MachineTypeUnion from, MachineTypeUnion to) { | 95   void CheckNop(MachineTypeUnion from, MachineTypeUnion to) { | 
| 100     Node* n = Parameter(0); | 96     Node* n = Parameter(0); | 
| 101     Node* c = changer()->GetRepresentationFor(n, from, to); | 97     Node* c = changer()->GetRepresentationFor(n, from, to); | 
| 102     CHECK_EQ(n, c); | 98     CHECK_EQ(n, c); | 
| 103   } | 99   } | 
| 104 }; | 100 }; | 
| 105 | 101 } | 
| 106 }  // namespace compiler | 102 } | 
| 107 }  // namespace internal | 103 }  // namespace v8::internal::compiler | 
| 108 }  // namespace v8 |  | 
| 109 | 104 | 
| 110 | 105 | 
| 111 static const MachineType all_reps[] = {kRepBit,     kRepWord32,  kRepWord64, | 106 static const MachineType all_reps[] = {kRepBit,     kRepWord32,  kRepWord64, | 
| 112                                        kRepFloat32, kRepFloat64, kRepTagged}; | 107                                        kRepFloat32, kRepFloat64, kRepTagged}; | 
| 113 | 108 | 
| 114 | 109 | 
| 115 TEST(ToBit_constant) { | 110 TEST(BoolToBit_constant) { | 
| 116   RepresentationChangerTester r; | 111   RepresentationChangerTester r; | 
| 117 | 112 | 
| 118   Node* true_node = r.jsgraph()->TrueConstant(); | 113   Node* true_node = r.jsgraph()->TrueConstant(); | 
| 119   Node* true_bit = | 114   Node* true_bit = | 
| 120       r.changer()->GetRepresentationFor(true_node, kRepTagged, kRepBit); | 115       r.changer()->GetRepresentationFor(true_node, kRepTagged, kRepBit); | 
| 121   r.CheckInt32Constant(true_bit, 1); | 116   r.CheckInt32Constant(true_bit, 1); | 
| 122 | 117 | 
| 123   Node* false_node = r.jsgraph()->FalseConstant(); | 118   Node* false_node = r.jsgraph()->FalseConstant(); | 
| 124   Node* false_bit = | 119   Node* false_bit = | 
| 125       r.changer()->GetRepresentationFor(false_node, kRepTagged, kRepBit); | 120       r.changer()->GetRepresentationFor(false_node, kRepTagged, kRepBit); | 
| 126   r.CheckInt32Constant(false_bit, 0); | 121   r.CheckInt32Constant(false_bit, 0); | 
| 127 |  | 
| 128   { |  | 
| 129     FOR_FLOAT64_INPUTS(i) { |  | 
| 130       Node* node = r.jsgraph()->Constant(*i); |  | 
| 131       Node* bit = r.changer()->GetRepresentationFor(node, kRepTagged, kRepBit); |  | 
| 132       r.CheckInt32Constant(bit, DoubleToBoolean(*i) ? 1 : 0); |  | 
| 133     } |  | 
| 134   } |  | 
| 135 |  | 
| 136   { |  | 
| 137     FOR_INT32_INPUTS(i) { |  | 
| 138       Node* node = r.jsgraph()->Int32Constant(*i); |  | 
| 139       Node* bit = r.changer()->GetRepresentationFor(node, kRepWord32, kRepBit); |  | 
| 140       r.CheckInt32Constant(bit, *i == 0 ? 0 : 1); |  | 
| 141     } |  | 
| 142   } |  | 
| 143 } | 122 } | 
| 144 | 123 | 
| 145 | 124 | 
| 146 TEST(BitToBool_constant) { | 125 TEST(BitToBool_constant) { | 
| 147   RepresentationChangerTester r; | 126   RepresentationChangerTester r; | 
| 148 | 127 | 
| 149   for (int i = -5; i < 5; i++) { | 128   for (int i = -5; i < 5; i++) { | 
| 150     Node* node = r.jsgraph()->Int32Constant(i); | 129     Node* node = r.jsgraph()->Int32Constant(i); | 
| 151     Node* val = r.changer()->GetRepresentationFor(node, kRepBit, kRepTagged); | 130     Node* val = r.changer()->GetRepresentationFor(node, kRepBit, kRepTagged); | 
| 152     r.CheckHeapConstant(val, i == 0 ? r.isolate()->heap()->false_value() | 131     r.CheckHeapConstant(val, i == 0 ? r.isolate()->heap()->false_value() | 
| (...skipping 231 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 384       Node* n = r.jsgraph()->Constant(static_cast<double>(*i)); | 363       Node* n = r.jsgraph()->Constant(static_cast<double>(*i)); | 
| 385       Node* c = r.changer()->GetRepresentationFor(n, kRepTagged | kTypeUint32, | 364       Node* c = r.changer()->GetRepresentationFor(n, kRepTagged | kTypeUint32, | 
| 386                                                   kRepWord32); | 365                                                   kRepWord32); | 
| 387       r.CheckUint32Constant(c, *i); | 366       r.CheckUint32Constant(c, *i); | 
| 388     } | 367     } | 
| 389   } | 368   } | 
| 390 } | 369 } | 
| 391 | 370 | 
| 392 | 371 | 
| 393 static void CheckChange(IrOpcode::Value expected, MachineTypeUnion from, | 372 static void CheckChange(IrOpcode::Value expected, MachineTypeUnion from, | 
| 394                         MachineTypeUnion to, Type* from_type = Type::Any()) { | 373                         MachineTypeUnion to) { | 
| 395   RepresentationChangerTester r; | 374   RepresentationChangerTester r; | 
| 396 | 375 | 
| 397   Node* n = r.Parameter(from_type); | 376   Node* n = r.Parameter(); | 
| 398   Node* c = r.changer()->GetRepresentationFor(n, from, to); | 377   Node* c = r.changer()->GetRepresentationFor(n, from, to); | 
| 399 | 378 | 
| 400   CHECK_NE(c, n); | 379   CHECK_NE(c, n); | 
| 401   CHECK_EQ(expected, c->opcode()); | 380   CHECK_EQ(expected, c->opcode()); | 
| 402   CHECK_EQ(n, c->InputAt(0)); | 381   CHECK_EQ(n, c->InputAt(0)); | 
| 403 } | 382 } | 
| 404 | 383 | 
| 405 | 384 | 
| 406 static void CheckTwoChanges(IrOpcode::Value expected2, | 385 static void CheckTwoChanges(IrOpcode::Value expected2, | 
| 407                             IrOpcode::Value expected1, MachineTypeUnion from, | 386                             IrOpcode::Value expected1, MachineTypeUnion from, | 
| 408                             MachineTypeUnion to, | 387                             MachineTypeUnion to) { | 
| 409                             Type* from_type = Type::Any()) { |  | 
| 410   RepresentationChangerTester r; | 388   RepresentationChangerTester r; | 
| 411 | 389 | 
| 412   Node* n = r.Parameter(from_type); | 390   Node* n = r.Parameter(); | 
| 413   Node* c1 = r.changer()->GetRepresentationFor(n, from, to); | 391   Node* c1 = r.changer()->GetRepresentationFor(n, from, to); | 
| 414 | 392 | 
| 415   CHECK_NE(c1, n); | 393   CHECK_NE(c1, n); | 
| 416   CHECK_EQ(expected1, c1->opcode()); | 394   CHECK_EQ(expected1, c1->opcode()); | 
| 417   Node* c2 = c1->InputAt(0); | 395   Node* c2 = c1->InputAt(0); | 
| 418   CHECK_NE(c2, n); | 396   CHECK_NE(c2, n); | 
| 419   CHECK_EQ(expected2, c2->opcode()); | 397   CHECK_EQ(expected2, c2->opcode()); | 
| 420   CHECK_EQ(n, c2->InputAt(0)); | 398   CHECK_EQ(n, c2->InputAt(0)); | 
| 421 } | 399 } | 
| 422 | 400 | 
| 423 | 401 | 
| 424 TEST(SingleChanges) { | 402 TEST(SingleChanges) { | 
| 425   CheckChange(IrOpcode::kChangeBoolToBit, kRepTagged, kRepBit, Type::Boolean()); | 403   CheckChange(IrOpcode::kChangeBoolToBit, kRepTagged, kRepBit); | 
| 426   CheckTwoChanges(IrOpcode::kChangeTaggedToInt32, IrOpcode::kChangeWord32ToBit, |  | 
| 427                   kRepTagged, kRepBit, Type::Signed32()); |  | 
| 428   CheckTwoChanges(IrOpcode::kChangeTaggedToUint32, IrOpcode::kChangeWord32ToBit, |  | 
| 429                   kRepTagged, kRepBit, Type::Unsigned32()); |  | 
| 430   CheckChange(IrOpcode::kChangeWord32ToBit, kRepWord8, kRepBit); |  | 
| 431   CheckChange(IrOpcode::kChangeWord32ToBit, kRepWord16, kRepBit); |  | 
| 432   CheckChange(IrOpcode::kChangeWord32ToBit, kRepWord32, kRepBit); |  | 
| 433   CheckChange(IrOpcode::kChangeWord64ToBit, kRepWord64, kRepBit); |  | 
| 434   CheckChange(IrOpcode::kChangeBitToBool, kRepBit, kRepTagged); | 404   CheckChange(IrOpcode::kChangeBitToBool, kRepBit, kRepTagged); | 
| 435 | 405 | 
| 436   CheckChange(IrOpcode::kChangeInt32ToTagged, kRepWord32 | kTypeInt32, | 406   CheckChange(IrOpcode::kChangeInt32ToTagged, kRepWord32 | kTypeInt32, | 
| 437               kRepTagged); | 407               kRepTagged); | 
| 438   CheckChange(IrOpcode::kChangeUint32ToTagged, kRepWord32 | kTypeUint32, | 408   CheckChange(IrOpcode::kChangeUint32ToTagged, kRepWord32 | kTypeUint32, | 
| 439               kRepTagged); | 409               kRepTagged); | 
| 440   CheckChange(IrOpcode::kChangeFloat64ToTagged, kRepFloat64, kRepTagged); | 410   CheckChange(IrOpcode::kChangeFloat64ToTagged, kRepFloat64, kRepTagged); | 
| 441 | 411 | 
| 442   CheckChange(IrOpcode::kChangeTaggedToInt32, kRepTagged | kTypeInt32, | 412   CheckChange(IrOpcode::kChangeTaggedToInt32, kRepTagged | kTypeInt32, | 
| 443               kRepWord32); | 413               kRepWord32); | 
| (...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 527   r.CheckNop(kRepBit, kRepWord32); | 497   r.CheckNop(kRepBit, kRepWord32); | 
| 528   r.CheckNop(kRepBit | kTypeBool, kRepWord32); | 498   r.CheckNop(kRepBit | kTypeBool, kRepWord32); | 
| 529   r.CheckNop(kRepBit, kRepWord64); | 499   r.CheckNop(kRepBit, kRepWord64); | 
| 530   r.CheckNop(kRepBit | kTypeBool, kRepWord64); | 500   r.CheckNop(kRepBit | kTypeBool, kRepWord64); | 
| 531 } | 501 } | 
| 532 | 502 | 
| 533 | 503 | 
| 534 TEST(TypeErrors) { | 504 TEST(TypeErrors) { | 
| 535   RepresentationChangerTester r; | 505   RepresentationChangerTester r; | 
| 536 | 506 | 
|  | 507   // Wordish cannot be implicitly converted to/from comparison conditions. | 
|  | 508   r.CheckTypeError(kRepWord8, kRepBit); | 
|  | 509   r.CheckTypeError(kRepWord8, kRepBit | kTypeBool); | 
|  | 510   r.CheckTypeError(kRepWord16, kRepBit); | 
|  | 511   r.CheckTypeError(kRepWord16, kRepBit | kTypeBool); | 
|  | 512   r.CheckTypeError(kRepWord32, kRepBit); | 
|  | 513   r.CheckTypeError(kRepWord32, kRepBit | kTypeBool); | 
|  | 514   r.CheckTypeError(kRepWord64, kRepBit); | 
|  | 515   r.CheckTypeError(kRepWord64, kRepBit | kTypeBool); | 
|  | 516 | 
| 537   // Floats cannot be implicitly converted to/from comparison conditions. | 517   // Floats cannot be implicitly converted to/from comparison conditions. | 
| 538   r.CheckTypeError(kRepFloat64, kRepBit); | 518   r.CheckTypeError(kRepFloat64, kRepBit); | 
| 539   r.CheckTypeError(kRepFloat64, kRepBit | kTypeBool); | 519   r.CheckTypeError(kRepFloat64, kRepBit | kTypeBool); | 
| 540   r.CheckTypeError(kRepBit, kRepFloat64); | 520   r.CheckTypeError(kRepBit, kRepFloat64); | 
| 541   r.CheckTypeError(kRepBit | kTypeBool, kRepFloat64); | 521   r.CheckTypeError(kRepBit | kTypeBool, kRepFloat64); | 
| 542 | 522 | 
| 543   // Floats cannot be implicitly converted to/from comparison conditions. | 523   // Floats cannot be implicitly converted to/from comparison conditions. | 
| 544   r.CheckTypeError(kRepFloat32, kRepBit); | 524   r.CheckTypeError(kRepFloat32, kRepBit); | 
| 545   r.CheckTypeError(kRepFloat32, kRepBit | kTypeBool); | 525   r.CheckTypeError(kRepFloat32, kRepBit | kTypeBool); | 
| 546   r.CheckTypeError(kRepBit, kRepFloat32); | 526   r.CheckTypeError(kRepBit, kRepFloat32); | 
| (...skipping 15 matching lines...) Expand all  Loading... | 
| 562   r.CheckTypeError(kRepWord32 | kTypeUint32, kRepWord64); | 542   r.CheckTypeError(kRepWord32 | kTypeUint32, kRepWord64); | 
| 563 | 543 | 
| 564   for (size_t i = 0; i < arraysize(all_reps); i++) { | 544   for (size_t i = 0; i < arraysize(all_reps); i++) { | 
| 565     for (size_t j = 0; j < arraysize(all_reps); j++) { | 545     for (size_t j = 0; j < arraysize(all_reps); j++) { | 
| 566       if (i == j) continue; | 546       if (i == j) continue; | 
| 567       // Only a single from representation is allowed. | 547       // Only a single from representation is allowed. | 
| 568       r.CheckTypeError(all_reps[i] | all_reps[j], kRepTagged); | 548       r.CheckTypeError(all_reps[i] | all_reps[j], kRepTagged); | 
| 569     } | 549     } | 
| 570   } | 550   } | 
| 571 } | 551 } | 
| OLD | NEW | 
|---|