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

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

Issue 1867913004: Specialize instance calls when the call receiver is the method receiver and the method class has a … (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: Created 4 years, 8 months 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
« no previous file with comments | « runtime/vm/flow_graph_compiler_ia32.cc ('k') | runtime/vm/flow_graph_compiler_x64.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
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/globals.h" // Needed here to get TARGET_ARCH_MIPS. 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_MIPS.
6 #if defined(TARGET_ARCH_MIPS) 6 #if defined(TARGET_ARCH_MIPS)
7 7
8 #include "vm/flow_graph_compiler.h" 8 #include "vm/flow_graph_compiler.h"
9 9
10 #include "vm/ast_printer.h" 10 #include "vm/ast_printer.h"
(...skipping 1602 matching lines...) Expand 10 before | Expand all | Expand 10 after
1613 #endif 1613 #endif
1614 1614
1615 1615
1616 void FlowGraphCompiler::EmitTestAndCall(const ICData& ic_data, 1616 void FlowGraphCompiler::EmitTestAndCall(const ICData& ic_data,
1617 intptr_t argument_count, 1617 intptr_t argument_count,
1618 const Array& argument_names, 1618 const Array& argument_names,
1619 Label* failed, 1619 Label* failed,
1620 Label* match_found, 1620 Label* match_found,
1621 intptr_t deopt_id, 1621 intptr_t deopt_id,
1622 TokenPosition token_index, 1622 TokenPosition token_index,
1623 LocationSummary* locs) { 1623 LocationSummary* locs,
1624 bool complete) {
1624 ASSERT(is_optimizing()); 1625 ASSERT(is_optimizing());
1625 __ Comment("EmitTestAndCall"); 1626 __ Comment("EmitTestAndCall");
1626 const Array& arguments_descriptor = 1627 const Array& arguments_descriptor =
1627 Array::ZoneHandle(zone(), ArgumentsDescriptor::New(argument_count, 1628 Array::ZoneHandle(zone(), ArgumentsDescriptor::New(argument_count,
1628 argument_names)); 1629 argument_names));
1629 1630
1630 // Load receiver into T0. 1631 // Load receiver into T0.
1631 __ LoadFromOffset(T0, SP, (argument_count - 1) * kWordSize); 1632 __ LoadFromOffset(T0, SP, (argument_count - 1) * kWordSize);
1632 __ LoadObject(S4, arguments_descriptor); 1633 __ LoadObject(S4, arguments_descriptor);
1633 1634
1634 const bool kFirstCheckIsSmi = ic_data.GetReceiverClassIdAt(0) == kSmiCid; 1635 const bool kFirstCheckIsSmi = ic_data.GetReceiverClassIdAt(0) == kSmiCid;
1635 const intptr_t kNumChecks = ic_data.NumberOfChecks(); 1636 const intptr_t kNumChecks = ic_data.NumberOfChecks();
1636 1637
1637 ASSERT(!ic_data.IsNull() && (kNumChecks > 0)); 1638 ASSERT(!ic_data.IsNull() && (kNumChecks > 0));
1638 1639
1639 Label after_smi_test; 1640 Label after_smi_test;
1640 __ andi(CMPRES1, T0, Immediate(kSmiTagMask));
1641 if (kFirstCheckIsSmi) { 1641 if (kFirstCheckIsSmi) {
1642 __ andi(CMPRES1, T0, Immediate(kSmiTagMask));
1642 // Jump if receiver is not Smi. 1643 // Jump if receiver is not Smi.
1643 if (kNumChecks == 1) { 1644 if (kNumChecks == 1) {
1644 __ bne(CMPRES1, ZR, failed); 1645 __ bne(CMPRES1, ZR, failed);
1645 } else { 1646 } else {
1646 __ bne(CMPRES1, ZR, &after_smi_test); 1647 __ bne(CMPRES1, ZR, &after_smi_test);
1647 } 1648 }
1648 // Do not use the code from the function, but let the code be patched so 1649 // Do not use the code from the function, but let the code be patched so
1649 // that we can record the outgoing edges to other code. 1650 // that we can record the outgoing edges to other code.
1650 const Function& function = Function::ZoneHandle( 1651 const Function& function = Function::ZoneHandle(
1651 zone(), ic_data.GetTargetAt(0)); 1652 zone(), ic_data.GetTargetAt(0));
1652 GenerateStaticDartCall(deopt_id, 1653 GenerateStaticDartCall(deopt_id,
1653 token_index, 1654 token_index,
1654 *StubCode::CallStaticFunction_entry(), 1655 *StubCode::CallStaticFunction_entry(),
1655 RawPcDescriptors::kOther, 1656 RawPcDescriptors::kOther,
1656 locs, 1657 locs,
1657 function); 1658 function);
1658 __ Drop(argument_count); 1659 __ Drop(argument_count);
1659 if (kNumChecks > 1) { 1660 if (kNumChecks > 1) {
1660 __ b(match_found); 1661 __ b(match_found);
1661 } 1662 }
1662 } else { 1663 } else {
1663 // Receiver is Smi, but Smi is not a valid class therefore fail. 1664 // Receiver is Smi, but Smi is not a valid class therefore fail.
1664 // (Smi class must be first in the list). 1665 // (Smi class must be first in the list).
1665 __ beq(CMPRES1, ZR, failed); 1666 if (!complete) {
1667 __ andi(CMPRES1, T0, Immediate(kSmiTagMask));
1668 __ beq(CMPRES1, ZR, failed);
1669 }
1666 } 1670 }
1667 1671
1668 __ Bind(&after_smi_test); 1672 __ Bind(&after_smi_test);
1669 1673
1670 GrowableArray<CidTarget> sorted(kNumChecks); 1674 GrowableArray<CidTarget> sorted(kNumChecks);
1671 SortICDataByCount(ic_data, &sorted, /* drop_smi = */ true); 1675 SortICDataByCount(ic_data, &sorted, /* drop_smi = */ true);
1672 1676
1673 // Value is not Smi, 1677 // Value is not Smi,
1674 const intptr_t kSortedLen = sorted.length(); 1678 const intptr_t kSortedLen = sorted.length();
1675 // If kSortedLen is 0 then only a Smi check was needed; the Smi check above 1679 // If kSortedLen is 0 then only a Smi check was needed; the Smi check above
1676 // will fail if there was only one check and receiver is not Smi. 1680 // will fail if there was only one check and receiver is not Smi.
1677 if (kSortedLen == 0) return; 1681 if (kSortedLen == 0) return;
1678 1682
1679 __ LoadClassId(T2, T0); 1683 __ LoadClassId(T2, T0);
1680 for (intptr_t i = 0; i < kSortedLen; i++) { 1684 for (intptr_t i = 0; i < kSortedLen; i++) {
1681 const bool kIsLastCheck = (i == (kSortedLen - 1)); 1685 const bool kIsLastCheck = (i == (kSortedLen - 1));
1682 ASSERT(sorted[i].cid != kSmiCid); 1686 ASSERT(sorted[i].cid != kSmiCid);
1683 Label next_test; 1687 Label next_test;
1684 if (kIsLastCheck) { 1688 if (!complete) {
1685 __ BranchNotEqual(T2, Immediate(sorted[i].cid), failed); 1689 if (kIsLastCheck) {
1690 __ BranchNotEqual(T2, Immediate(sorted[i].cid), failed);
1691 } else {
1692 __ BranchNotEqual(T2, Immediate(sorted[i].cid), &next_test);
1693 }
1686 } else { 1694 } else {
1687 __ BranchNotEqual(T2, Immediate(sorted[i].cid), &next_test); 1695 if (!kIsLastCheck) {
1696 __ BranchNotEqual(T2, Immediate(sorted[i].cid), &next_test);
1697 }
1688 } 1698 }
1689 // Do not use the code from the function, but let the code be patched so 1699 // Do not use the code from the function, but let the code be patched so
1690 // that we can record the outgoing edges to other code. 1700 // that we can record the outgoing edges to other code.
1691 const Function& function = *sorted[i].target; 1701 const Function& function = *sorted[i].target;
1692 GenerateStaticDartCall(deopt_id, 1702 GenerateStaticDartCall(deopt_id,
1693 token_index, 1703 token_index,
1694 *StubCode::CallStaticFunction_entry(), 1704 *StubCode::CallStaticFunction_entry(),
1695 RawPcDescriptors::kOther, 1705 RawPcDescriptors::kOther,
1696 locs, 1706 locs,
1697 function); 1707 function);
(...skipping 244 matching lines...) Expand 10 before | Expand all | Expand 10 after
1942 __ AddImmediate(SP, kDoubleSize); 1952 __ AddImmediate(SP, kDoubleSize);
1943 } 1953 }
1944 1954
1945 1955
1946 #undef __ 1956 #undef __
1947 1957
1948 1958
1949 } // namespace dart 1959 } // namespace dart
1950 1960
1951 #endif // defined TARGET_ARCH_MIPS 1961 #endif // defined TARGET_ARCH_MIPS
OLDNEW
« no previous file with comments | « runtime/vm/flow_graph_compiler_ia32.cc ('k') | runtime/vm/flow_graph_compiler_x64.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698