Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(89)

Side by Side Diff: runtime/vm/flow_graph_optimizer.cc

Issue 51373004: SIMD shuffle API changes (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 7 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #include "vm/flow_graph_optimizer.h" 5 #include "vm/flow_graph_optimizer.h"
6 6
7 #include "vm/bit_vector.h" 7 #include "vm/bit_vector.h"
8 #include "vm/cha.h" 8 #include "vm/cha.h"
9 #include "vm/dart_entry.h" 9 #include "vm/dart_entry.h"
10 #include "vm/flow_graph_builder.h" 10 #include "vm/flow_graph_builder.h"
(...skipping 1674 matching lines...) Expand 10 before | Expand all | Expand 10 after
1685 if (!ShouldInlineSimd()) { 1685 if (!ShouldInlineSimd()) {
1686 return false; 1686 return false;
1687 } 1687 }
1688 AddCheckClass(call->ArgumentAt(0), 1688 AddCheckClass(call->ArgumentAt(0),
1689 ICData::ZoneHandle( 1689 ICData::ZoneHandle(
1690 call->ic_data()->AsUnaryClassChecksForArgNr(0)), 1690 call->ic_data()->AsUnaryClassChecksForArgNr(0)),
1691 call->deopt_id(), 1691 call->deopt_id(),
1692 call->env(), 1692 call->env(),
1693 call); 1693 call);
1694 intptr_t mask = 0; 1694 intptr_t mask = 0;
1695 if (getter == MethodRecognizer::kFloat32x4Shuffle) { 1695 if ((getter == MethodRecognizer::kFloat32x4Shuffle) ||
1696 (getter == MethodRecognizer::kFloat32x4ShuffleMix)) {
1696 // Extract shuffle mask. 1697 // Extract shuffle mask.
1697 ASSERT(call->ArgumentCount() == 2); 1698 Definition* mask_definition = NULL;
1698 Definition* mask_definition = call->ArgumentAt(1); 1699 if (getter == MethodRecognizer::kFloat32x4Shuffle) {
1700 ASSERT(call->ArgumentCount() == 2);
1701 mask_definition = call->ArgumentAt(1);
1702 } else {
1703 ASSERT(getter == MethodRecognizer::kFloat32x4ShuffleMix);
1704 ASSERT(call->ArgumentCount() == 3);
1705 mask_definition = call->ArgumentAt(2);
1706 }
1699 if (!mask_definition->IsConstant()) { 1707 if (!mask_definition->IsConstant()) {
1700 // Not a constant. 1708 // Not a constant.
1701 return false; 1709 return false;
1702 } 1710 }
1703 ASSERT(mask_definition->IsConstant()); 1711 ASSERT(mask_definition->IsConstant());
1704 ConstantInstr* constant_instruction = mask_definition->AsConstant(); 1712 ConstantInstr* constant_instruction = mask_definition->AsConstant();
1705 const Object& constant_mask = constant_instruction->value(); 1713 const Object& constant_mask = constant_instruction->value();
1706 if (!constant_mask.IsSmi()) { 1714 if (!constant_mask.IsSmi()) {
1707 // Not a smi. 1715 // Not a smi.
1708 return false; 1716 return false;
1709 } 1717 }
1710 ASSERT(constant_mask.IsSmi()); 1718 ASSERT(constant_mask.IsSmi());
1711 mask = Smi::Cast(constant_mask).Value(); 1719 mask = Smi::Cast(constant_mask).Value();
1712 if (mask < 0 || mask > 255) { 1720 if (mask < 0 || mask > 255) {
1713 // Not a valid mask. 1721 // Not a valid mask.
1714 return false; 1722 return false;
1715 } 1723 }
1716 } 1724 }
1717 if (getter == MethodRecognizer::kFloat32x4GetSignMask) { 1725 if (getter == MethodRecognizer::kFloat32x4GetSignMask) {
1718 Simd32x4GetSignMaskInstr* instr = new Simd32x4GetSignMaskInstr( 1726 Simd32x4GetSignMaskInstr* instr = new Simd32x4GetSignMaskInstr(
1719 getter, 1727 getter,
1720 new Value(call->ArgumentAt(0)), 1728 new Value(call->ArgumentAt(0)),
1721 call->deopt_id()); 1729 call->deopt_id());
1722 ReplaceCall(call, instr); 1730 ReplaceCall(call, instr);
1723 return true; 1731 return true;
1732 } else if (getter == MethodRecognizer::kFloat32x4ShuffleMix) {
1733 Simd32x4ShuffleMixInstr* instr = new Simd32x4ShuffleMixInstr(
1734 getter,
1735 new Value(call->ArgumentAt(0)),
1736 new Value(call->ArgumentAt(1)),
1737 mask,
1738 call->deopt_id());
1739 ReplaceCall(call, instr);
1740 return true;
1724 } else { 1741 } else {
1725 ASSERT((getter == MethodRecognizer::kFloat32x4Shuffle) || 1742 ASSERT((getter == MethodRecognizer::kFloat32x4Shuffle) ||
1726 (getter == MethodRecognizer::kFloat32x4ShuffleX) || 1743 (getter == MethodRecognizer::kFloat32x4ShuffleX) ||
1727 (getter == MethodRecognizer::kFloat32x4ShuffleY) || 1744 (getter == MethodRecognizer::kFloat32x4ShuffleY) ||
1728 (getter == MethodRecognizer::kFloat32x4ShuffleZ) || 1745 (getter == MethodRecognizer::kFloat32x4ShuffleZ) ||
1729 (getter == MethodRecognizer::kFloat32x4ShuffleW)); 1746 (getter == MethodRecognizer::kFloat32x4ShuffleW));
1730 Float32x4ShuffleInstr* instr = new Float32x4ShuffleInstr( 1747 Simd32x4ShuffleInstr* instr = new Simd32x4ShuffleInstr(
1731 getter, 1748 getter,
1732 new Value(call->ArgumentAt(0)), 1749 new Value(call->ArgumentAt(0)),
1733 mask, 1750 mask,
1734 call->deopt_id()); 1751 call->deopt_id());
1735 ReplaceCall(call, instr); 1752 ReplaceCall(call, instr);
1736 return true; 1753 return true;
1737 } 1754 }
1738 UNREACHABLE(); 1755 UNREACHABLE();
1739 return false; 1756 return false;
1740 } 1757 }
1741 1758
1742 1759
1743 bool FlowGraphOptimizer::InlineUint32x4Getter(InstanceCallInstr* call, 1760 bool FlowGraphOptimizer::InlineUint32x4Getter(InstanceCallInstr* call,
1744 MethodRecognizer::Kind getter) { 1761 MethodRecognizer::Kind getter) {
1745 if (!ShouldInlineSimd()) { 1762 if (!ShouldInlineSimd()) {
1746 return false; 1763 return false;
1747 } 1764 }
1748 AddCheckClass(call->ArgumentAt(0), 1765 AddCheckClass(call->ArgumentAt(0),
1749 ICData::ZoneHandle( 1766 ICData::ZoneHandle(
1750 call->ic_data()->AsUnaryClassChecksForArgNr(0)), 1767 call->ic_data()->AsUnaryClassChecksForArgNr(0)),
1751 call->deopt_id(), 1768 call->deopt_id(),
1752 call->env(), 1769 call->env(),
1753 call); 1770 call);
1771 intptr_t mask = 0;
1772 if ((getter == MethodRecognizer::kUint32x4Shuffle) ||
1773 (getter == MethodRecognizer::kUint32x4ShuffleMix)) {
1774 // Extract shuffle mask.
1775 Definition* mask_definition = NULL;
1776 if (getter == MethodRecognizer::kUint32x4Shuffle) {
1777 ASSERT(call->ArgumentCount() == 2);
1778 mask_definition = call->ArgumentAt(1);
1779 } else {
1780 ASSERT(getter == MethodRecognizer::kUint32x4ShuffleMix);
1781 ASSERT(call->ArgumentCount() == 3);
1782 mask_definition = call->ArgumentAt(2);
1783 }
1784 if (!mask_definition->IsConstant()) {
1785 // Not a constant.
srdjan 2013/11/01 05:51:41 This comment is redundant, I think.
Cutch 2013/11/01 07:06:30 Done.
1786 return false;
1787 }
1788 ASSERT(mask_definition->IsConstant());
1789 ConstantInstr* constant_instruction = mask_definition->AsConstant();
1790 const Object& constant_mask = constant_instruction->value();
1791 if (!constant_mask.IsSmi()) {
1792 // Not a smi.
srdjan 2013/11/01 05:51:41 Ditto
Cutch 2013/11/01 07:06:30 Done.
1793 return false;
1794 }
1795 ASSERT(constant_mask.IsSmi());
1796 mask = Smi::Cast(constant_mask).Value();
1797 if (mask < 0 || mask > 255) {
srdjan 2013/11/01 05:51:41 Add parentheses.
Cutch 2013/11/01 07:06:30 Done.
1798 // Not a valid mask.
1799 return false;
1800 }
1801 }
1754 if (getter == MethodRecognizer::kUint32x4GetSignMask) { 1802 if (getter == MethodRecognizer::kUint32x4GetSignMask) {
1755 Simd32x4GetSignMaskInstr* instr = new Simd32x4GetSignMaskInstr( 1803 Simd32x4GetSignMaskInstr* instr = new Simd32x4GetSignMaskInstr(
1756 getter, 1804 getter,
1757 new Value(call->ArgumentAt(0)), 1805 new Value(call->ArgumentAt(0)),
1758 call->deopt_id()); 1806 call->deopt_id());
1759 ReplaceCall(call, instr); 1807 ReplaceCall(call, instr);
1760 return true; 1808 return true;
1809 } else if (getter == MethodRecognizer::kUint32x4ShuffleMix) {
1810 Simd32x4ShuffleMixInstr* instr = new Simd32x4ShuffleMixInstr(
1811 getter,
1812 new Value(call->ArgumentAt(0)),
1813 new Value(call->ArgumentAt(1)),
1814 mask,
1815 call->deopt_id());
1816 ReplaceCall(call, instr);
1817 return true;
1818 } else if (getter == MethodRecognizer::kUint32x4Shuffle) {
1819 Simd32x4ShuffleInstr* instr = new Simd32x4ShuffleInstr(
1820 getter,
1821 new Value(call->ArgumentAt(0)),
1822 mask,
1823 call->deopt_id());
1824 ReplaceCall(call, instr);
1825 return true;
1761 } else { 1826 } else {
1762 Uint32x4GetFlagInstr* instr = new Uint32x4GetFlagInstr( 1827 Uint32x4GetFlagInstr* instr = new Uint32x4GetFlagInstr(
1763 getter, 1828 getter,
1764 new Value(call->ArgumentAt(0)), 1829 new Value(call->ArgumentAt(0)),
1765 call->deopt_id()); 1830 call->deopt_id());
1766 ReplaceCall(call, instr); 1831 ReplaceCall(call, instr);
1767 return true; 1832 return true;
1768 } 1833 }
1769 } 1834 }
1770 1835
(...skipping 542 matching lines...) Expand 10 before | Expand all | Expand 10 after
2313 call->ic_data()->AsUnaryClassChecksForArgNr(0)), 2378 call->ic_data()->AsUnaryClassChecksForArgNr(0)),
2314 call->deopt_id(), 2379 call->deopt_id(),
2315 call->env(), 2380 call->env(),
2316 call); 2381 call);
2317 Float32x4MinMaxInstr* minmax = 2382 Float32x4MinMaxInstr* minmax =
2318 new Float32x4MinMaxInstr(recognized_kind, new Value(left), 2383 new Float32x4MinMaxInstr(recognized_kind, new Value(left),
2319 new Value(right), call->deopt_id()); 2384 new Value(right), call->deopt_id());
2320 ReplaceCall(call, minmax); 2385 ReplaceCall(call, minmax);
2321 return true; 2386 return true;
2322 } 2387 }
2323 case MethodRecognizer::kFloat32x4WithZWInXY:
2324 case MethodRecognizer::kFloat32x4InterleaveXY:
2325 case MethodRecognizer::kFloat32x4InterleaveZW:
2326 case MethodRecognizer::kFloat32x4InterleaveXYPairs:
2327 case MethodRecognizer::kFloat32x4InterleaveZWPairs: {
2328 Definition* left = call->ArgumentAt(0);
2329 Definition* right = call->ArgumentAt(1);
2330 // Type check left.
2331 AddCheckClass(left,
2332 ICData::ZoneHandle(
2333 call->ic_data()->AsUnaryClassChecksForArgNr(0)),
2334 call->deopt_id(),
2335 call->env(),
2336 call);
2337 Float32x4TwoArgShuffleInstr* two_arg_shuffle =
2338 new Float32x4TwoArgShuffleInstr(recognized_kind, new Value(left),
2339 new Value(right), call->deopt_id());
2340 ReplaceCall(call, two_arg_shuffle);
2341 return true;
2342 }
2343 case MethodRecognizer::kFloat32x4Scale: { 2388 case MethodRecognizer::kFloat32x4Scale: {
2344 Definition* left = call->ArgumentAt(0); 2389 Definition* left = call->ArgumentAt(0);
2345 Definition* right = call->ArgumentAt(1); 2390 Definition* right = call->ArgumentAt(1);
2346 // Type check left. 2391 // Type check left.
2347 AddCheckClass(left, 2392 AddCheckClass(left,
2348 ICData::ZoneHandle( 2393 ICData::ZoneHandle(
2349 call->ic_data()->AsUnaryClassChecksForArgNr(0)), 2394 call->ic_data()->AsUnaryClassChecksForArgNr(0)),
2350 call->deopt_id(), 2395 call->deopt_id(),
2351 call->env(), 2396 call->env(),
2352 call); 2397 call);
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after
2422 call->deopt_id(), 2467 call->deopt_id(),
2423 call->env(), 2468 call->env(),
2424 call); 2469 call);
2425 Float32x4ClampInstr* clamp = new Float32x4ClampInstr(new Value(left), 2470 Float32x4ClampInstr* clamp = new Float32x4ClampInstr(new Value(left),
2426 new Value(lower), 2471 new Value(lower),
2427 new Value(upper), 2472 new Value(upper),
2428 call->deopt_id()); 2473 call->deopt_id());
2429 ReplaceCall(call, clamp); 2474 ReplaceCall(call, clamp);
2430 return true; 2475 return true;
2431 } 2476 }
2477 case MethodRecognizer::kFloat32x4ShuffleMix:
2432 case MethodRecognizer::kFloat32x4Shuffle: { 2478 case MethodRecognizer::kFloat32x4Shuffle: {
2433 return InlineFloat32x4Getter(call, recognized_kind); 2479 return InlineFloat32x4Getter(call, recognized_kind);
2434 } 2480 }
2435 default: 2481 default:
2436 return false; 2482 return false;
2437 } 2483 }
2438 } 2484 }
2439 2485
2440 2486
2441 bool FlowGraphOptimizer::TryInlineUint32x4Method( 2487 bool FlowGraphOptimizer::TryInlineUint32x4Method(
2442 InstanceCallInstr* call, 2488 InstanceCallInstr* call,
2443 MethodRecognizer::Kind recognized_kind) { 2489 MethodRecognizer::Kind recognized_kind) {
2444 if (!ShouldInlineSimd()) { 2490 if (!ShouldInlineSimd()) {
2445 return false; 2491 return false;
2446 } 2492 }
2447 ASSERT(call->HasICData()); 2493 ASSERT(call->HasICData());
2448 switch (recognized_kind) { 2494 switch (recognized_kind) {
2495 case MethodRecognizer::kUint32x4ShuffleMix:
2496 case MethodRecognizer::kUint32x4Shuffle:
2449 case MethodRecognizer::kUint32x4GetFlagX: 2497 case MethodRecognizer::kUint32x4GetFlagX:
2450 case MethodRecognizer::kUint32x4GetFlagY: 2498 case MethodRecognizer::kUint32x4GetFlagY:
2451 case MethodRecognizer::kUint32x4GetFlagZ: 2499 case MethodRecognizer::kUint32x4GetFlagZ:
2452 case MethodRecognizer::kUint32x4GetFlagW: 2500 case MethodRecognizer::kUint32x4GetFlagW:
2453 case MethodRecognizer::kUint32x4GetSignMask: 2501 case MethodRecognizer::kUint32x4GetSignMask:
2454 ASSERT(call->ic_data()->HasReceiverClassId(kUint32x4Cid)); 2502 ASSERT(call->ic_data()->HasReceiverClassId(kUint32x4Cid));
2455 ASSERT(call->ic_data()->HasOneTarget()); 2503 ASSERT(call->ic_data()->HasOneTarget());
2456 return InlineUint32x4Getter(call, recognized_kind); 2504 return InlineUint32x4Getter(call, recognized_kind);
2457 2505
2458 case MethodRecognizer::kUint32x4Select: { 2506 case MethodRecognizer::kUint32x4Select: {
(...skipping 4419 matching lines...) Expand 10 before | Expand all | Expand 10 after
6878 } 6926 }
6879 } 6927 }
6880 6928
6881 6929
6882 void ConstantPropagator::VisitFloat32x4Constructor( 6930 void ConstantPropagator::VisitFloat32x4Constructor(
6883 Float32x4ConstructorInstr* instr) { 6931 Float32x4ConstructorInstr* instr) {
6884 SetValue(instr, non_constant_); 6932 SetValue(instr, non_constant_);
6885 } 6933 }
6886 6934
6887 6935
6888 void ConstantPropagator::VisitFloat32x4Shuffle(Float32x4ShuffleInstr* instr) { 6936 void ConstantPropagator::VisitSimd32x4Shuffle(Simd32x4ShuffleInstr* instr) {
6889 SetValue(instr, non_constant_); 6937 SetValue(instr, non_constant_);
6890 } 6938 }
6891 6939
6940
6941 void ConstantPropagator::VisitSimd32x4ShuffleMix(
6942 Simd32x4ShuffleMixInstr* instr) {
6943 SetValue(instr, non_constant_);
6944 }
6945
6892 6946
6893 void ConstantPropagator::VisitSimd32x4GetSignMask( 6947 void ConstantPropagator::VisitSimd32x4GetSignMask(
6894 Simd32x4GetSignMaskInstr* instr) { 6948 Simd32x4GetSignMaskInstr* instr) {
6895 SetValue(instr, non_constant_); 6949 SetValue(instr, non_constant_);
6896 } 6950 }
6897 6951
6898 6952
6899 void ConstantPropagator::VisitFloat32x4Zero(Float32x4ZeroInstr* instr) { 6953 void ConstantPropagator::VisitFloat32x4Zero(Float32x4ZeroInstr* instr) {
6900 SetValue(instr, non_constant_); 6954 SetValue(instr, non_constant_);
6901 } 6955 }
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
6941 SetValue(instr, non_constant_); 6995 SetValue(instr, non_constant_);
6942 } 6996 }
6943 6997
6944 6998
6945 void ConstantPropagator::VisitFloat32x4ToUint32x4( 6999 void ConstantPropagator::VisitFloat32x4ToUint32x4(
6946 Float32x4ToUint32x4Instr* instr) { 7000 Float32x4ToUint32x4Instr* instr) {
6947 SetValue(instr, non_constant_); 7001 SetValue(instr, non_constant_);
6948 } 7002 }
6949 7003
6950 7004
6951 void ConstantPropagator::VisitFloat32x4TwoArgShuffle(
6952 Float32x4TwoArgShuffleInstr* instr) {
6953 SetValue(instr, non_constant_);
6954 }
6955
6956
6957 void ConstantPropagator::VisitUint32x4BoolConstructor( 7005 void ConstantPropagator::VisitUint32x4BoolConstructor(
6958 Uint32x4BoolConstructorInstr* instr) { 7006 Uint32x4BoolConstructorInstr* instr) {
6959 SetValue(instr, non_constant_); 7007 SetValue(instr, non_constant_);
6960 } 7008 }
6961 7009
6962 7010
6963 void ConstantPropagator::VisitUint32x4GetFlag(Uint32x4GetFlagInstr* instr) { 7011 void ConstantPropagator::VisitUint32x4GetFlag(Uint32x4GetFlagInstr* instr) {
6964 SetValue(instr, non_constant_); 7012 SetValue(instr, non_constant_);
6965 } 7013 }
6966 7014
(...skipping 956 matching lines...) Expand 10 before | Expand all | Expand 10 after
7923 } 7971 }
7924 7972
7925 // Insert materializations at environment uses. 7973 // Insert materializations at environment uses.
7926 for (intptr_t i = 0; i < exits.length(); i++) { 7974 for (intptr_t i = 0; i < exits.length(); i++) {
7927 CreateMaterializationAt(exits[i], alloc, alloc->cls(), *fields); 7975 CreateMaterializationAt(exits[i], alloc, alloc->cls(), *fields);
7928 } 7976 }
7929 } 7977 }
7930 7978
7931 7979
7932 } // namespace dart 7980 } // namespace dart
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698