| 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 "test/unittests/compiler/node-test-utils.h" | 5 #include "test/unittests/compiler/node-test-utils.h" |
| 6 | 6 |
| 7 #include <vector> |
| 8 |
| 7 #include "src/assembler.h" | 9 #include "src/assembler.h" |
| 8 #include "src/compiler/node-properties.h" | 10 #include "src/compiler/node-properties.h" |
| 9 #include "src/compiler/simplified-operator.h" | 11 #include "src/compiler/simplified-operator.h" |
| 10 #include "src/unique.h" | 12 #include "src/unique.h" |
| 11 | 13 |
| 12 using testing::_; | 14 using testing::_; |
| 13 using testing::MakeMatcher; | 15 using testing::MakeMatcher; |
| 14 using testing::MatcherInterface; | 16 using testing::MatcherInterface; |
| 15 using testing::MatchResultListener; | 17 using testing::MatchResultListener; |
| 16 using testing::StringMatchResultListener; | 18 using testing::StringMatchResultListener; |
| 17 | 19 |
| 18 namespace v8 { | 20 namespace v8 { |
| 19 namespace internal { | 21 namespace internal { |
| 20 namespace compiler { | 22 namespace compiler { |
| 21 | 23 |
| 22 namespace { | 24 namespace { |
| 23 | 25 |
| 24 template <typename T> | 26 template <typename T> |
| 25 bool PrintMatchAndExplain(const T& value, const char* value_name, | 27 bool PrintMatchAndExplain(const T& value, const std::string& value_name, |
| 26 const Matcher<T>& value_matcher, | 28 const Matcher<T>& value_matcher, |
| 27 MatchResultListener* listener) { | 29 MatchResultListener* listener) { |
| 28 StringMatchResultListener value_listener; | 30 StringMatchResultListener value_listener; |
| 29 if (!value_matcher.MatchAndExplain(value, &value_listener)) { | 31 if (!value_matcher.MatchAndExplain(value, &value_listener)) { |
| 30 *listener << "whose " << value_name << " " << value << " doesn't match"; | 32 *listener << "whose " << value_name << " " << value << " doesn't match"; |
| 31 if (value_listener.str() != "") { | 33 if (value_listener.str() != "") { |
| 32 *listener << ", " << value_listener.str(); | 34 *listener << ", " << value_listener.str(); |
| 33 } | 35 } |
| 34 return false; | 36 return false; |
| 35 } | 37 } |
| (...skipping 556 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 592 PrintMatchAndExplain(NodeProperties::GetValueInput(node, 0), "base", | 594 PrintMatchAndExplain(NodeProperties::GetValueInput(node, 0), "base", |
| 593 base_matcher_, listener)); | 595 base_matcher_, listener)); |
| 594 } | 596 } |
| 595 | 597 |
| 596 private: | 598 private: |
| 597 const Matcher<size_t> index_matcher_; | 599 const Matcher<size_t> index_matcher_; |
| 598 const Matcher<Node*> base_matcher_; | 600 const Matcher<Node*> base_matcher_; |
| 599 }; | 601 }; |
| 600 | 602 |
| 601 | 603 |
| 602 class IsCall2Matcher final : public NodeMatcher { | 604 class IsCallMatcher final : public NodeMatcher { |
| 603 public: | 605 public: |
| 604 IsCall2Matcher(const Matcher<CallDescriptor*>& descriptor_matcher, | 606 IsCallMatcher(const Matcher<CallDescriptor*>& descriptor_matcher, |
| 605 const Matcher<Node*>& value0_matcher, | 607 const std::vector<Matcher<Node*>>& value_matchers, |
| 606 const Matcher<Node*>& value1_matcher, | 608 const Matcher<Node*>& effect_matcher, |
| 607 const Matcher<Node*>& effect_matcher, | 609 const Matcher<Node*>& control_matcher) |
| 608 const Matcher<Node*>& control_matcher) | |
| 609 : NodeMatcher(IrOpcode::kCall), | 610 : NodeMatcher(IrOpcode::kCall), |
| 610 descriptor_matcher_(descriptor_matcher), | 611 descriptor_matcher_(descriptor_matcher), |
| 611 value0_matcher_(value0_matcher), | 612 value_matchers_(value_matchers), |
| 612 value1_matcher_(value1_matcher), | |
| 613 effect_matcher_(effect_matcher), | 613 effect_matcher_(effect_matcher), |
| 614 control_matcher_(control_matcher) {} | 614 control_matcher_(control_matcher) {} |
| 615 | 615 |
| 616 void DescribeTo(std::ostream* os) const final { | 616 void DescribeTo(std::ostream* os) const final { |
| 617 NodeMatcher::DescribeTo(os); | 617 NodeMatcher::DescribeTo(os); |
| 618 *os << " whose value0 ("; | 618 for (size_t i = 0; i < value_matchers_.size(); ++i) { |
| 619 value0_matcher_.DescribeTo(os); | 619 if (i == 0) { |
| 620 *os << ") and value1 ("; | 620 *os << " whose value0 ("; |
| 621 value1_matcher_.DescribeTo(os); | 621 } else { |
| 622 *os << ") and effect ("; | 622 *os << "), value" << i << " ("; |
| 623 } |
| 624 value_matchers_[i].DescribeTo(os); |
| 625 } |
| 626 *os << "), effect ("; |
| 623 effect_matcher_.DescribeTo(os); | 627 effect_matcher_.DescribeTo(os); |
| 624 *os << ") and control ("; | 628 *os << ") and control ("; |
| 625 control_matcher_.DescribeTo(os); | 629 control_matcher_.DescribeTo(os); |
| 626 *os << ")"; | |
| 627 } | |
| 628 | |
| 629 bool MatchAndExplain(Node* node, MatchResultListener* listener) const final { | |
| 630 return (NodeMatcher::MatchAndExplain(node, listener) && | |
| 631 PrintMatchAndExplain(OpParameter<CallDescriptor*>(node), | |
| 632 "descriptor", descriptor_matcher_, listener) && | |
| 633 PrintMatchAndExplain(NodeProperties::GetValueInput(node, 0), | |
| 634 "value0", value0_matcher_, listener) && | |
| 635 PrintMatchAndExplain(NodeProperties::GetValueInput(node, 1), | |
| 636 "value1", value1_matcher_, listener) && | |
| 637 PrintMatchAndExplain(NodeProperties::GetEffectInput(node), "effect", | |
| 638 effect_matcher_, listener) && | |
| 639 PrintMatchAndExplain(NodeProperties::GetControlInput(node), | |
| 640 "control", control_matcher_, listener)); | |
| 641 } | |
| 642 | |
| 643 private: | |
| 644 const Matcher<CallDescriptor*> descriptor_matcher_; | |
| 645 const Matcher<Node*> value0_matcher_; | |
| 646 const Matcher<Node*> value1_matcher_; | |
| 647 const Matcher<Node*> effect_matcher_; | |
| 648 const Matcher<Node*> control_matcher_; | |
| 649 }; | |
| 650 | |
| 651 | |
| 652 class IsCall4Matcher final : public NodeMatcher { | |
| 653 public: | |
| 654 IsCall4Matcher(const Matcher<CallDescriptor*>& descriptor_matcher, | |
| 655 const Matcher<Node*>& value0_matcher, | |
| 656 const Matcher<Node*>& value1_matcher, | |
| 657 const Matcher<Node*>& value2_matcher, | |
| 658 const Matcher<Node*>& value3_matcher, | |
| 659 const Matcher<Node*>& effect_matcher, | |
| 660 const Matcher<Node*>& control_matcher) | |
| 661 : NodeMatcher(IrOpcode::kCall), | |
| 662 descriptor_matcher_(descriptor_matcher), | |
| 663 value0_matcher_(value0_matcher), | |
| 664 value1_matcher_(value1_matcher), | |
| 665 value2_matcher_(value2_matcher), | |
| 666 value3_matcher_(value3_matcher), | |
| 667 effect_matcher_(effect_matcher), | |
| 668 control_matcher_(control_matcher) {} | |
| 669 | |
| 670 void DescribeTo(std::ostream* os) const final { | |
| 671 NodeMatcher::DescribeTo(os); | |
| 672 *os << " whose value0 ("; | |
| 673 value0_matcher_.DescribeTo(os); | |
| 674 *os << ") and value1 ("; | |
| 675 value1_matcher_.DescribeTo(os); | |
| 676 *os << ") and value2 ("; | |
| 677 value2_matcher_.DescribeTo(os); | |
| 678 *os << ") and value3 ("; | |
| 679 value3_matcher_.DescribeTo(os); | |
| 680 *os << ") and effect ("; | |
| 681 effect_matcher_.DescribeTo(os); | |
| 682 *os << ") and control ("; | |
| 683 control_matcher_.DescribeTo(os); | |
| 684 *os << ")"; | 630 *os << ")"; |
| 685 } | 631 } |
| 686 | 632 |
| 687 bool MatchAndExplain(Node* node, MatchResultListener* listener) const final { | 633 bool MatchAndExplain(Node* node, MatchResultListener* listener) const final { |
| 688 return (NodeMatcher::MatchAndExplain(node, listener) && | 634 if (!NodeMatcher::MatchAndExplain(node, listener) || |
| 689 PrintMatchAndExplain(OpParameter<CallDescriptor*>(node), | 635 !PrintMatchAndExplain(OpParameter<CallDescriptor*>(node), "descriptor", |
| 690 "descriptor", descriptor_matcher_, listener) && | 636 descriptor_matcher_, listener)) { |
| 691 PrintMatchAndExplain(NodeProperties::GetValueInput(node, 0), | 637 return false; |
| 692 "value0", value0_matcher_, listener) && | 638 } |
| 693 PrintMatchAndExplain(NodeProperties::GetValueInput(node, 1), | 639 for (size_t i = 0; i < value_matchers_.size(); ++i) { |
| 694 "value1", value1_matcher_, listener) && | 640 std::ostringstream ost; |
| 695 PrintMatchAndExplain(NodeProperties::GetValueInput(node, 2), | 641 ost << "value" << i; |
| 696 "value2", value2_matcher_, listener) && | 642 if (!PrintMatchAndExplain( |
| 697 PrintMatchAndExplain(NodeProperties::GetValueInput(node, 3), | 643 NodeProperties::GetValueInput(node, static_cast<int>(i)), |
| 698 "value3", value3_matcher_, listener) && | 644 ost.str(), value_matchers_[i], listener)) { |
| 699 PrintMatchAndExplain(NodeProperties::GetEffectInput(node), "effect", | 645 return false; |
| 646 } |
| 647 } |
| 648 return (PrintMatchAndExplain(NodeProperties::GetEffectInput(node), "effect", |
| 700 effect_matcher_, listener) && | 649 effect_matcher_, listener) && |
| 701 PrintMatchAndExplain(NodeProperties::GetControlInput(node), | 650 PrintMatchAndExplain(NodeProperties::GetControlInput(node), |
| 702 "control", control_matcher_, listener)); | 651 "control", control_matcher_, listener)); |
| 703 } | 652 } |
| 704 | 653 |
| 705 private: | 654 private: |
| 706 const Matcher<CallDescriptor*> descriptor_matcher_; | 655 const Matcher<CallDescriptor*> descriptor_matcher_; |
| 707 const Matcher<Node*> value0_matcher_; | 656 const std::vector<Matcher<Node*>> value_matchers_; |
| 708 const Matcher<Node*> value1_matcher_; | |
| 709 const Matcher<Node*> value2_matcher_; | |
| 710 const Matcher<Node*> value3_matcher_; | |
| 711 const Matcher<Node*> effect_matcher_; | 657 const Matcher<Node*> effect_matcher_; |
| 712 const Matcher<Node*> control_matcher_; | 658 const Matcher<Node*> control_matcher_; |
| 713 }; | 659 }; |
| 714 | 660 |
| 715 | 661 |
| 716 class IsLoadFieldMatcher final : public NodeMatcher { | 662 class IsLoadFieldMatcher final : public NodeMatcher { |
| 717 public: | 663 public: |
| 718 IsLoadFieldMatcher(const Matcher<FieldAccess>& access_matcher, | 664 IsLoadFieldMatcher(const Matcher<FieldAccess>& access_matcher, |
| 719 const Matcher<Node*>& base_matcher, | 665 const Matcher<Node*>& base_matcher, |
| 720 const Matcher<Node*>& effect_matcher, | 666 const Matcher<Node*>& effect_matcher, |
| (...skipping 728 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1449 const Matcher<Node*>& base_matcher) { | 1395 const Matcher<Node*>& base_matcher) { |
| 1450 return MakeMatcher(new IsProjectionMatcher(index_matcher, base_matcher)); | 1396 return MakeMatcher(new IsProjectionMatcher(index_matcher, base_matcher)); |
| 1451 } | 1397 } |
| 1452 | 1398 |
| 1453 | 1399 |
| 1454 Matcher<Node*> IsCall(const Matcher<CallDescriptor*>& descriptor_matcher, | 1400 Matcher<Node*> IsCall(const Matcher<CallDescriptor*>& descriptor_matcher, |
| 1455 const Matcher<Node*>& value0_matcher, | 1401 const Matcher<Node*>& value0_matcher, |
| 1456 const Matcher<Node*>& value1_matcher, | 1402 const Matcher<Node*>& value1_matcher, |
| 1457 const Matcher<Node*>& effect_matcher, | 1403 const Matcher<Node*>& effect_matcher, |
| 1458 const Matcher<Node*>& control_matcher) { | 1404 const Matcher<Node*>& control_matcher) { |
| 1459 return MakeMatcher(new IsCall2Matcher(descriptor_matcher, value0_matcher, | 1405 std::vector<Matcher<Node*>> value_matchers; |
| 1460 value1_matcher, effect_matcher, | 1406 value_matchers.push_back(value0_matcher); |
| 1461 control_matcher)); | 1407 value_matchers.push_back(value1_matcher); |
| 1408 return MakeMatcher(new IsCallMatcher(descriptor_matcher, value_matchers, |
| 1409 effect_matcher, control_matcher)); |
| 1462 } | 1410 } |
| 1463 | 1411 |
| 1464 | 1412 |
| 1413 Matcher<Node*> IsCall(const Matcher<CallDescriptor*>& descriptor_matcher, |
| 1414 const Matcher<Node*>& value0_matcher, |
| 1415 const Matcher<Node*>& value1_matcher, |
| 1416 const Matcher<Node*>& value2_matcher, |
| 1417 const Matcher<Node*>& value3_matcher, |
| 1418 const Matcher<Node*>& value4_matcher, |
| 1419 const Matcher<Node*>& effect_matcher, |
| 1420 const Matcher<Node*>& control_matcher) { |
| 1421 std::vector<Matcher<Node*>> value_matchers; |
| 1422 value_matchers.push_back(value0_matcher); |
| 1423 value_matchers.push_back(value1_matcher); |
| 1424 value_matchers.push_back(value2_matcher); |
| 1425 value_matchers.push_back(value3_matcher); |
| 1426 value_matchers.push_back(value4_matcher); |
| 1427 return MakeMatcher(new IsCallMatcher(descriptor_matcher, value_matchers, |
| 1428 effect_matcher, control_matcher)); |
| 1429 } |
| 1430 |
| 1431 |
| 1465 Matcher<Node*> IsCall(const Matcher<CallDescriptor*>& descriptor_matcher, | 1432 Matcher<Node*> IsCall(const Matcher<CallDescriptor*>& descriptor_matcher, |
| 1466 const Matcher<Node*>& value0_matcher, | 1433 const Matcher<Node*>& value0_matcher, |
| 1467 const Matcher<Node*>& value1_matcher, | 1434 const Matcher<Node*>& value1_matcher, |
| 1468 const Matcher<Node*>& value2_matcher, | 1435 const Matcher<Node*>& value2_matcher, |
| 1469 const Matcher<Node*>& value3_matcher, | 1436 const Matcher<Node*>& value3_matcher, |
| 1437 const Matcher<Node*>& value4_matcher, |
| 1438 const Matcher<Node*>& value5_matcher, |
| 1470 const Matcher<Node*>& effect_matcher, | 1439 const Matcher<Node*>& effect_matcher, |
| 1471 const Matcher<Node*>& control_matcher) { | 1440 const Matcher<Node*>& control_matcher) { |
| 1472 return MakeMatcher(new IsCall4Matcher( | 1441 std::vector<Matcher<Node*>> value_matchers; |
| 1473 descriptor_matcher, value0_matcher, value1_matcher, value2_matcher, | 1442 value_matchers.push_back(value0_matcher); |
| 1474 value3_matcher, effect_matcher, control_matcher)); | 1443 value_matchers.push_back(value1_matcher); |
| 1444 value_matchers.push_back(value2_matcher); |
| 1445 value_matchers.push_back(value3_matcher); |
| 1446 value_matchers.push_back(value4_matcher); |
| 1447 value_matchers.push_back(value5_matcher); |
| 1448 return MakeMatcher(new IsCallMatcher(descriptor_matcher, value_matchers, |
| 1449 effect_matcher, control_matcher)); |
| 1475 } | 1450 } |
| 1476 | 1451 |
| 1477 | 1452 |
| 1453 Matcher<Node*> IsCall( |
| 1454 const Matcher<CallDescriptor*>& descriptor_matcher, |
| 1455 const Matcher<Node*>& value0_matcher, const Matcher<Node*>& value1_matcher, |
| 1456 const Matcher<Node*>& value2_matcher, const Matcher<Node*>& value3_matcher, |
| 1457 const Matcher<Node*>& value4_matcher, const Matcher<Node*>& value5_matcher, |
| 1458 const Matcher<Node*>& value6_matcher, const Matcher<Node*>& effect_matcher, |
| 1459 const Matcher<Node*>& control_matcher) { |
| 1460 std::vector<Matcher<Node*>> value_matchers; |
| 1461 value_matchers.push_back(value0_matcher); |
| 1462 value_matchers.push_back(value1_matcher); |
| 1463 value_matchers.push_back(value2_matcher); |
| 1464 value_matchers.push_back(value3_matcher); |
| 1465 value_matchers.push_back(value4_matcher); |
| 1466 value_matchers.push_back(value5_matcher); |
| 1467 value_matchers.push_back(value6_matcher); |
| 1468 return MakeMatcher(new IsCallMatcher(descriptor_matcher, value_matchers, |
| 1469 effect_matcher, control_matcher)); |
| 1470 } |
| 1471 |
| 1472 |
| 1478 Matcher<Node*> IsLoadField(const Matcher<FieldAccess>& access_matcher, | 1473 Matcher<Node*> IsLoadField(const Matcher<FieldAccess>& access_matcher, |
| 1479 const Matcher<Node*>& base_matcher, | 1474 const Matcher<Node*>& base_matcher, |
| 1480 const Matcher<Node*>& effect_matcher, | 1475 const Matcher<Node*>& effect_matcher, |
| 1481 const Matcher<Node*>& control_matcher) { | 1476 const Matcher<Node*>& control_matcher) { |
| 1482 return MakeMatcher(new IsLoadFieldMatcher(access_matcher, base_matcher, | 1477 return MakeMatcher(new IsLoadFieldMatcher(access_matcher, base_matcher, |
| 1483 effect_matcher, control_matcher)); | 1478 effect_matcher, control_matcher)); |
| 1484 } | 1479 } |
| 1485 | 1480 |
| 1486 | 1481 |
| 1487 Matcher<Node*> IsStoreField(const Matcher<FieldAccess>& access_matcher, | 1482 Matcher<Node*> IsStoreField(const Matcher<FieldAccess>& access_matcher, |
| (...skipping 149 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1637 IS_UNOP_MATCHER(NumberToInt32) | 1632 IS_UNOP_MATCHER(NumberToInt32) |
| 1638 IS_UNOP_MATCHER(NumberToUint32) | 1633 IS_UNOP_MATCHER(NumberToUint32) |
| 1639 IS_UNOP_MATCHER(ObjectIsSmi) | 1634 IS_UNOP_MATCHER(ObjectIsSmi) |
| 1640 IS_UNOP_MATCHER(ObjectIsNonNegativeSmi) | 1635 IS_UNOP_MATCHER(ObjectIsNonNegativeSmi) |
| 1641 IS_UNOP_MATCHER(Word32Clz) | 1636 IS_UNOP_MATCHER(Word32Clz) |
| 1642 #undef IS_UNOP_MATCHER | 1637 #undef IS_UNOP_MATCHER |
| 1643 | 1638 |
| 1644 } // namespace compiler | 1639 } // namespace compiler |
| 1645 } // namespace internal | 1640 } // namespace internal |
| 1646 } // namespace v8 | 1641 } // namespace v8 |
| OLD | NEW |