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

Side by Side Diff: src/a64/stub-cache-a64.cc

Issue 136643008: A64: Synchronize with r18256. (Closed) Base URL: https://v8.googlecode.com/svn/branches/experimental/a64
Patch Set: Created 6 years, 10 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 | Annotate | Revision Log
« no previous file with comments | « src/a64/macro-assembler-a64.cc ('k') | src/allocation-tracker.h » ('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 2013 the V8 project authors. All rights reserved. 1 // Copyright 2013 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 686 matching lines...) Expand 10 before | Expand all | Expand 10 after
697 void StoreStubCompiler::GenerateRestoreName(MacroAssembler* masm, 697 void StoreStubCompiler::GenerateRestoreName(MacroAssembler* masm,
698 Label* label, 698 Label* label,
699 Handle<Name> name) { 699 Handle<Name> name) {
700 if (!label->is_unused()) { 700 if (!label->is_unused()) {
701 __ Bind(label); 701 __ Bind(label);
702 __ Mov(this->name(), Operand(name)); 702 __ Mov(this->name(), Operand(name));
703 } 703 }
704 } 704 }
705 705
706 706
707 // The function to called must be passed in x1.
708 static void GenerateCallFunction(MacroAssembler* masm,
709 Handle<Object> object,
710 const ParameterCount& arguments,
711 Label* miss,
712 ExtraICState extra_ic_state,
713 Register function,
714 Register receiver,
715 Register scratch) {
716 ASSERT(!AreAliased(function, receiver, scratch));
717 ASSERT(function.Is(x1));
718
719 // Check that the function really is a function.
720 __ JumpIfSmi(function, miss);
721 __ JumpIfNotObjectType(function, scratch, scratch, JS_FUNCTION_TYPE, miss);
722
723 if (object->IsGlobalObject()) {
724 const int argc = arguments.immediate();
725 const int receiver_offset = argc * kPointerSize;
726 __ Ldr(scratch,
727 FieldMemOperand(receiver, GlobalObject::kGlobalReceiverOffset));
728 __ Poke(scratch, receiver_offset);
729 }
730
731 // Invoke the function.
732 CallKind call_kind = CallICBase::Contextual::decode(extra_ic_state)
733 ? CALL_AS_FUNCTION
734 : CALL_AS_METHOD;
735 __ InvokeFunction(
736 function, arguments, JUMP_FUNCTION, NullCallWrapper(), call_kind);
737 }
738
739
740 static void PushInterceptorArguments(MacroAssembler* masm, 707 static void PushInterceptorArguments(MacroAssembler* masm,
741 Register receiver, 708 Register receiver,
742 Register holder, 709 Register holder,
743 Register name, 710 Register name,
744 Handle<JSObject> holder_obj) { 711 Handle<JSObject> holder_obj) {
745 STATIC_ASSERT(StubCache::kInterceptorArgsNameIndex == 0); 712 STATIC_ASSERT(StubCache::kInterceptorArgsNameIndex == 0);
746 STATIC_ASSERT(StubCache::kInterceptorArgsInfoIndex == 1); 713 STATIC_ASSERT(StubCache::kInterceptorArgsInfoIndex == 1);
747 STATIC_ASSERT(StubCache::kInterceptorArgsThisIndex == 2); 714 STATIC_ASSERT(StubCache::kInterceptorArgsThisIndex == 2);
748 STATIC_ASSERT(StubCache::kInterceptorArgsHolderIndex == 3); 715 STATIC_ASSERT(StubCache::kInterceptorArgsHolderIndex == 3);
749 STATIC_ASSERT(StubCache::kInterceptorArgsLength == 4); 716 STATIC_ASSERT(StubCache::kInterceptorArgsLength == 4);
(...skipping 181 matching lines...) Expand 10 before | Expand all | Expand 10 after
931 ASSERT(!AreAliased(receiver, scratch, values[i])); 898 ASSERT(!AreAliased(receiver, scratch, values[i]));
932 __ Poke(receiver, index-- * kPointerSize); 899 __ Poke(receiver, index-- * kPointerSize);
933 } 900 }
934 901
935 GenerateFastApiDirectCall(masm, optimization, argc, true); 902 GenerateFastApiDirectCall(masm, optimization, argc, true);
936 } 903 }
937 904
938 905
939 class CallInterceptorCompiler BASE_EMBEDDED { 906 class CallInterceptorCompiler BASE_EMBEDDED {
940 public: 907 public:
941 CallInterceptorCompiler(StubCompiler* stub_compiler, 908 CallInterceptorCompiler(CallStubCompiler* stub_compiler,
942 const ParameterCount& arguments, 909 const ParameterCount& arguments,
943 Register name, 910 Register name,
944 ExtraICState extra_ic_state) 911 ExtraICState extra_ic_state)
945 : stub_compiler_(stub_compiler), 912 : stub_compiler_(stub_compiler),
946 arguments_(arguments), 913 arguments_(arguments),
947 name_(name), 914 name_(name),
948 extra_ic_state_(extra_ic_state) {} 915 extra_ic_state_(extra_ic_state) {}
949 916
950 void Compile(MacroAssembler* masm, 917 void Compile(MacroAssembler* masm,
951 Handle<JSObject> object, 918 Handle<JSObject> object,
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after
1046 // safe to omit it here, as if present, it should be fetched 1013 // safe to omit it here, as if present, it should be fetched
1047 // by the previous CheckPrototypes. 1014 // by the previous CheckPrototypes.
1048 ASSERT(depth2 == kInvalidProtoDepth); 1015 ASSERT(depth2 == kInvalidProtoDepth);
1049 } 1016 }
1050 1017
1051 // Invoke function. 1018 // Invoke function.
1052 if (can_do_fast_api_call) { 1019 if (can_do_fast_api_call) {
1053 GenerateFastApiDirectCall( 1020 GenerateFastApiDirectCall(
1054 masm, optimization, arguments_.immediate(), false); 1021 masm, optimization, arguments_.immediate(), false);
1055 } else { 1022 } else {
1056 CallKind call_kind = CallICBase::Contextual::decode(extra_ic_state_)
1057 ? CALL_AS_FUNCTION
1058 : CALL_AS_METHOD;
1059 Handle<JSFunction> function = optimization.constant_function(); 1023 Handle<JSFunction> function = optimization.constant_function();
1060 ParameterCount expected(function); 1024 stub_compiler_->GenerateJumpFunctionIgnoreReceiver(function);
1061 __ InvokeFunction(function, expected, arguments_,
1062 JUMP_FUNCTION, NullCallWrapper(), call_kind);
1063 } 1025 }
1064 1026
1065 // Deferred code for fast API call case, clean preallocated space. 1027 // Deferred code for fast API call case, clean preallocated space.
1066 if (can_do_fast_api_call) { 1028 if (can_do_fast_api_call) {
1067 __ Bind(&miss_cleanup); 1029 __ Bind(&miss_cleanup);
1068 FreeSpaceForFastApiCall(masm); 1030 FreeSpaceForFastApiCall(masm);
1069 __ B(miss_label); 1031 __ B(miss_label);
1070 } 1032 }
1071 1033
1072 // Invoke a regular function. 1034 // Invoke a regular function.
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
1117 IC::kLoadPropertyWithInterceptorOnly); 1079 IC::kLoadPropertyWithInterceptorOnly);
1118 __ Pop(name_, receiver); 1080 __ Pop(name_, receiver);
1119 } 1081 }
1120 1082
1121 // If interceptor returns no-result sentinel, call the constant function. 1083 // If interceptor returns no-result sentinel, call the constant function.
1122 __ JumpIfNotRoot(x0, 1084 __ JumpIfNotRoot(x0,
1123 Heap::kNoInterceptorResultSentinelRootIndex, 1085 Heap::kNoInterceptorResultSentinelRootIndex,
1124 interceptor_succeeded); 1086 interceptor_succeeded);
1125 } 1087 }
1126 1088
1127 StubCompiler* stub_compiler_; 1089 CallStubCompiler* stub_compiler_;
1128 const ParameterCount& arguments_; 1090 const ParameterCount& arguments_;
1129 Register name_; 1091 Register name_;
1130 ExtraICState extra_ic_state_; 1092 ExtraICState extra_ic_state_;
1131 }; 1093 };
1132 1094
1133 1095
1134 void StubCompiler::GenerateTailCall(MacroAssembler* masm, Handle<Code> code) { 1096 void StubCompiler::GenerateTailCall(MacroAssembler* masm, Handle<Code> code) {
1135 __ Jump(code, RelocInfo::CODE_TARGET); 1097 __ Jump(code, RelocInfo::CODE_TARGET);
1136 } 1098 }
1137 1099
(...skipping 424 matching lines...) Expand 10 before | Expand all | Expand 10 after
1562 void CallStubCompiler::GenerateNameCheck(Handle<Name> name, Label* miss) { 1524 void CallStubCompiler::GenerateNameCheck(Handle<Name> name, Label* miss) {
1563 Register name_reg = x2; 1525 Register name_reg = x2;
1564 1526
1565 if (kind_ == Code::KEYED_CALL_IC) { 1527 if (kind_ == Code::KEYED_CALL_IC) {
1566 __ Cmp(name_reg, Operand(name)); 1528 __ Cmp(name_reg, Operand(name));
1567 __ B(ne, miss); 1529 __ B(ne, miss);
1568 } 1530 }
1569 } 1531 }
1570 1532
1571 1533
1534 void CallStubCompiler::GenerateFunctionCheck(Register function,
1535 Register scratch,
1536 Label* miss) {
1537 __ JumpIfSmi(function, miss);
1538 __ JumpIfNotObjectType(function, scratch, scratch, JS_FUNCTION_TYPE, miss);
1539 }
1540
1541
1572 // Load the function object into x1 register. 1542 // Load the function object into x1 register.
1573 void CallStubCompiler::GenerateLoadFunctionFromCell( 1543 void CallStubCompiler::GenerateLoadFunctionFromCell(
1574 Handle<Cell> cell, 1544 Handle<Cell> cell,
1575 Handle<JSFunction> function, 1545 Handle<JSFunction> function,
1576 Label* miss) { 1546 Label* miss) {
1577 // Get the value from the cell. 1547 // Get the value from the cell.
1578 __ Mov(x3, Operand(cell)); 1548 __ Mov(x3, Operand(cell));
1579 Register function_reg = x1; 1549 Register function_reg = x1;
1580 __ Ldr(function_reg, FieldMemOperand(x3, Cell::kValueOffset)); 1550 __ Ldr(function_reg, FieldMemOperand(x3, Cell::kValueOffset));
1581 1551
1582 // Check that the cell contains the same function. 1552 // Check that the cell contains the same function.
1583 if (heap()->InNewSpace(*function)) { 1553 if (heap()->InNewSpace(*function)) {
1584 // We can't embed a pointer to a function in new space so we have 1554 // We can't embed a pointer to a function in new space so we have
1585 // to verify that the shared function info is unchanged. This has 1555 // to verify that the shared function info is unchanged. This has
1586 // the nice side effect that multiple closures based on the same 1556 // the nice side effect that multiple closures based on the same
1587 // function can all use this call IC. Before we load through the 1557 // function can all use this call IC. Before we load through the
1588 // function, we have to verify that it still is a function. 1558 // function, we have to verify that it still is a function.
1589 __ JumpIfSmi(function_reg, miss); 1559 GenerateFunctionCheck(function_reg, x3, miss);
1590 __ JumpIfNotObjectType(function_reg, x3, x3, JS_FUNCTION_TYPE, miss);
1591 1560
1592 // Check the shared function info. Make sure it hasn't changed. 1561 // Check the shared function info. Make sure it hasn't changed.
1593 __ Mov(x3, Operand(Handle<SharedFunctionInfo>(function->shared()))); 1562 __ Mov(x3, Operand(Handle<SharedFunctionInfo>(function->shared())));
1594 __ Ldr(x4, 1563 __ Ldr(x4,
1595 FieldMemOperand(function_reg, JSFunction::kSharedFunctionInfoOffset)); 1564 FieldMemOperand(function_reg, JSFunction::kSharedFunctionInfoOffset));
1596 __ Cmp(x4, x3); 1565 __ Cmp(x4, x3);
1597 } else { 1566 } else {
1598 __ Cmp(function_reg, Operand(function)); 1567 __ Cmp(function_reg, Operand(function));
1599 } 1568 }
1600 __ B(ne, miss); 1569 __ B(ne, miss);
1601 } 1570 }
1602 1571
1603 1572
1604 void CallStubCompiler::GenerateMissBranch() { 1573 void CallStubCompiler::GenerateMissBranch() {
1605 Handle<Code> code = 1574 Handle<Code> code =
1606 isolate()->stub_cache()->ComputeCallMiss(arguments().immediate(), 1575 isolate()->stub_cache()->ComputeCallMiss(arguments().immediate(),
1607 kind_, 1576 kind_,
1608 extra_state_); 1577 extra_state());
1609 __ Jump(code, RelocInfo::CODE_TARGET); 1578 __ Jump(code, RelocInfo::CODE_TARGET);
1610 } 1579 }
1611 1580
1612 1581
1613 Handle<Code> CallStubCompiler::CompileCallField(Handle<JSObject> object, 1582 Handle<Code> CallStubCompiler::CompileCallField(Handle<JSObject> object,
1614 Handle<JSObject> holder, 1583 Handle<JSObject> holder,
1615 PropertyIndex index, 1584 PropertyIndex index,
1616 Handle<Name> name) { 1585 Handle<Name> name) {
1617 Label miss; 1586 Label miss;
1618 Register receiver = x0;
1619 Register function = x1; 1587 Register function = x1;
1620 1588
1621 Register holder_reg = HandlerFrontendHeader( 1589 Register holder_reg = HandlerFrontendHeader(
1622 object, holder, name, RECEIVER_MAP_CHECK, &miss); 1590 object, holder, name, RECEIVER_MAP_CHECK, &miss);
1623 1591
1624 GenerateFastPropertyLoad(masm(), function, holder_reg, 1592 GenerateFastPropertyLoad(masm(), function, holder_reg,
1625 index.is_inobject(holder), 1593 index.is_inobject(holder),
1626 index.translate(holder), 1594 index.translate(holder),
1627 Representation::Tagged()); 1595 Representation::Tagged());
1628 1596 GenerateJumpFunction(object, function, &miss);
1629 GenerateCallFunction(
1630 masm(), object, arguments(), &miss, extra_state_, function, receiver, x3);
1631 1597
1632 HandlerFrontendFooter(&miss); 1598 HandlerFrontendFooter(&miss);
1633 1599
1634 // Return the generated code. 1600 // Return the generated code.
1635 return GetCode(Code::FAST, name); 1601 return GetCode(Code::FAST, name);
1636 } 1602 }
1637 1603
1638 1604
1639 Handle<Code> CallStubCompiler::CompileArrayCodeCall( 1605 Handle<Code> CallStubCompiler::CompileArrayCodeCall(
1640 Handle<Object> object, 1606 Handle<Object> object,
(...skipping 28 matching lines...) Expand all
1669 } 1635 }
1670 1636
1671 1637
1672 Handle<Code> CallStubCompiler::CompileArrayPushCall( 1638 Handle<Code> CallStubCompiler::CompileArrayPushCall(
1673 Handle<Object> object, 1639 Handle<Object> object,
1674 Handle<JSObject> holder, 1640 Handle<JSObject> holder,
1675 Handle<Cell> cell, 1641 Handle<Cell> cell,
1676 Handle<JSFunction> function, 1642 Handle<JSFunction> function,
1677 Handle<String> name, 1643 Handle<String> name,
1678 Code::StubType type) { 1644 Code::StubType type) {
1679 // If object is not an array or is observed, bail out to regular call. 1645 // If object is not an array or is observed or sealed, bail out to regular
1646 // call.
1680 if (!object->IsJSArray() || 1647 if (!object->IsJSArray() ||
1681 !cell.is_null() || 1648 !cell.is_null() ||
1682 Handle<JSArray>::cast(object)->map()->is_observed()) { 1649 Handle<JSArray>::cast(object)->map()->is_observed() ||
1650 !Handle<JSArray>::cast(object)->map()->is_extensible()) {
1683 return Handle<Code>::null(); 1651 return Handle<Code>::null();
1684 } 1652 }
1685 1653
1686 Label miss; 1654 Label miss;
1687 1655
1688 HandlerFrontendHeader(object, holder, name, RECEIVER_MAP_CHECK, &miss); 1656 HandlerFrontendHeader(object, holder, name, RECEIVER_MAP_CHECK, &miss);
1689 1657
1690 Register receiver = x0; 1658 Register receiver = x0;
1691 1659
1692 const int argc = arguments().immediate(); 1660 const int argc = arguments().immediate();
(...skipping 235 matching lines...) Expand 10 before | Expand all | Expand 10 after
1928 } 1896 }
1929 1897
1930 1898
1931 Handle<Code> CallStubCompiler::CompileArrayPopCall( 1899 Handle<Code> CallStubCompiler::CompileArrayPopCall(
1932 Handle<Object> object, 1900 Handle<Object> object,
1933 Handle<JSObject> holder, 1901 Handle<JSObject> holder,
1934 Handle<Cell> cell, 1902 Handle<Cell> cell,
1935 Handle<JSFunction> function, 1903 Handle<JSFunction> function,
1936 Handle<String> name, 1904 Handle<String> name,
1937 Code::StubType type) { 1905 Code::StubType type) {
1938 // If object is not an array or is observed, bail out to regular call. 1906 // If object is not an array or is observed or sealed, bail out to regular
1907 // call.
1939 if (!object->IsJSArray() || 1908 if (!object->IsJSArray() ||
1940 !cell.is_null() || 1909 !cell.is_null() ||
1941 Handle<JSArray>::cast(object)->map()->is_observed()) { 1910 Handle<JSArray>::cast(object)->map()->is_observed() ||
1911 !Handle<JSArray>::cast(object)->map()->is_extensible()) {
1942 return Handle<Code>::null(); 1912 return Handle<Code>::null();
1943 } 1913 }
1944 1914
1945 const int argc = arguments().immediate(); 1915 const int argc = arguments().immediate();
1946 Label miss, return_undefined, call_builtin; 1916 Label miss, return_undefined, call_builtin;
1947 Register receiver = x0; 1917 Register receiver = x0;
1948 Register result = x1; 1918 Register result = x1;
1949 Register elements = x3; 1919 Register elements = x3;
1950 Register length = x4; 1920 Register length = x4;
1951 1921
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after
2007 Code::StubType type) { 1977 Code::StubType type) {
2008 // If object is not a string, bail out to regular call. 1978 // If object is not a string, bail out to regular call.
2009 if (!object->IsString() || !cell.is_null()) return Handle<Code>::null(); 1979 if (!object->IsString() || !cell.is_null()) return Handle<Code>::null();
2010 1980
2011 Label miss; 1981 Label miss;
2012 Label name_miss; 1982 Label name_miss;
2013 Label index_out_of_range; 1983 Label index_out_of_range;
2014 Label* index_out_of_range_label = &index_out_of_range; 1984 Label* index_out_of_range_label = &index_out_of_range;
2015 1985
2016 if (kind_ == Code::CALL_IC && 1986 if (kind_ == Code::CALL_IC &&
2017 (CallICBase::StringStubState::decode(extra_state_) == 1987 (CallICBase::StringStubState::decode(extra_state()) ==
2018 DEFAULT_STRING_STUB)) { 1988 DEFAULT_STRING_STUB)) {
2019 index_out_of_range_label = &miss; 1989 index_out_of_range_label = &miss;
2020 } 1990 }
2021 HandlerFrontendHeader(object, holder, name, STRING_CHECK, &name_miss); 1991 HandlerFrontendHeader(object, holder, name, STRING_CHECK, &name_miss);
2022 1992
2023 Register receiver = x0; 1993 Register receiver = x0;
2024 Register result = x1; 1994 Register result = x1;
2025 Register index = x4; 1995 Register index = x4;
2026 1996
2027 const int argc = arguments().immediate(); 1997 const int argc = arguments().immediate();
(...skipping 22 matching lines...) Expand all
2050 if (index_out_of_range.is_linked()) { 2020 if (index_out_of_range.is_linked()) {
2051 __ Bind(&index_out_of_range); 2021 __ Bind(&index_out_of_range);
2052 __ LoadRoot(x0, Heap::kNanValueRootIndex); 2022 __ LoadRoot(x0, Heap::kNanValueRootIndex);
2053 __ Drop(argc + 1); 2023 __ Drop(argc + 1);
2054 __ Ret(); 2024 __ Ret();
2055 } 2025 }
2056 2026
2057 __ Bind(&miss); 2027 __ Bind(&miss);
2058 // Restore function name in x2. 2028 // Restore function name in x2.
2059 __ Mov(x2, Operand(name)); 2029 __ Mov(x2, Operand(name));
2060 __ Bind(&name_miss); 2030 HandlerFrontendFooter(&name_miss);
2061 GenerateMissBranch();
2062 2031
2063 // Return the generated code. 2032 // Return the generated code.
2064 return GetCode(type, name); 2033 return GetCode(type, name);
2065 } 2034 }
2066 2035
2067 2036
2068 Handle<Code> CallStubCompiler::CompileStringCharAtCall( 2037 Handle<Code> CallStubCompiler::CompileStringCharAtCall(
2069 Handle<Object> object, 2038 Handle<Object> object,
2070 Handle<JSObject> holder, 2039 Handle<JSObject> holder,
2071 Handle<Cell> cell, 2040 Handle<Cell> cell,
2072 Handle<JSFunction> function, 2041 Handle<JSFunction> function,
2073 Handle<String> name, 2042 Handle<String> name,
2074 Code::StubType type) { 2043 Code::StubType type) {
2075 // If object is not a string, bail out to regular call. 2044 // If object is not a string, bail out to regular call.
2076 if (!object->IsString() || !cell.is_null()) return Handle<Code>::null(); 2045 if (!object->IsString() || !cell.is_null()) return Handle<Code>::null();
2077 2046
2078 const int argc = arguments().immediate(); 2047 const int argc = arguments().immediate();
2079 Label miss; 2048 Label miss;
2080 Label name_miss; 2049 Label name_miss;
2081 Label index_out_of_range; 2050 Label index_out_of_range;
2082 Label* index_out_of_range_label = &index_out_of_range; 2051 Label* index_out_of_range_label = &index_out_of_range;
2083 2052
2084 if (kind_ == Code::CALL_IC && 2053 if (kind_ == Code::CALL_IC &&
2085 (CallICBase::StringStubState::decode(extra_state_) == 2054 (CallICBase::StringStubState::decode(extra_state()) ==
2086 DEFAULT_STRING_STUB)) { 2055 DEFAULT_STRING_STUB)) {
2087 index_out_of_range_label = &miss; 2056 index_out_of_range_label = &miss;
2088 } 2057 }
2089 2058
2090 HandlerFrontendHeader(object, holder, name, STRING_CHECK, &name_miss); 2059 HandlerFrontendHeader(object, holder, name, STRING_CHECK, &name_miss);
2091 2060
2092 Register receiver = x0; 2061 Register receiver = x0;
2093 Register index = x4; 2062 Register index = x4;
2094 Register scratch = x3; 2063 Register scratch = x3;
2095 Register result = x1; 2064 Register result = x1;
(...skipping 23 matching lines...) Expand all
2119 if (index_out_of_range.is_linked()) { 2088 if (index_out_of_range.is_linked()) {
2120 __ Bind(&index_out_of_range); 2089 __ Bind(&index_out_of_range);
2121 __ LoadRoot(x0, Heap::kempty_stringRootIndex); 2090 __ LoadRoot(x0, Heap::kempty_stringRootIndex);
2122 __ Drop(argc + 1); 2091 __ Drop(argc + 1);
2123 __ Ret(); 2092 __ Ret();
2124 } 2093 }
2125 2094
2126 __ Bind(&miss); 2095 __ Bind(&miss);
2127 // Restore function name in x2. 2096 // Restore function name in x2.
2128 __ Mov(x2, Operand(name)); 2097 __ Mov(x2, Operand(name));
2129 __ Bind(&name_miss); 2098 HandlerFrontendFooter(&name_miss);
2130 GenerateMissBranch();
2131 2099
2132 // Return the generated code. 2100 // Return the generated code.
2133 return GetCode(type, name); 2101 return GetCode(type, name);
2134 } 2102 }
2135 2103
2136 2104
2137 Handle<Code> CallStubCompiler::CompileStringFromCharCodeCall( 2105 Handle<Code> CallStubCompiler::CompileStringFromCharCodeCall(
2138 Handle<Object> object, 2106 Handle<Object> object,
2139 Handle<JSObject> holder, 2107 Handle<JSObject> holder,
2140 Handle<Cell> cell, 2108 Handle<Cell> cell,
(...skipping 27 matching lines...) Expand all
2168 2136
2169 Register result = x0; 2137 Register result = x0;
2170 StringCharFromCodeGenerator generator(code, result); 2138 StringCharFromCodeGenerator generator(code, result);
2171 generator.GenerateFast(masm()); 2139 generator.GenerateFast(masm());
2172 __ Drop(argc + 1); 2140 __ Drop(argc + 1);
2173 __ Ret(); 2141 __ Ret();
2174 2142
2175 StubRuntimeCallHelper call_helper; 2143 StubRuntimeCallHelper call_helper;
2176 generator.GenerateSlow(masm(), call_helper); 2144 generator.GenerateSlow(masm(), call_helper);
2177 2145
2178 // Tail call the full function. We do not have to patch the receiver
2179 // because the function makes no use of it.
2180 __ Bind(&slow); 2146 __ Bind(&slow);
2181 ParameterCount expected(function); 2147 // We do not have to patch the receiver because the function makes no use of
2182 __ InvokeFunction(function, expected, arguments(), 2148 // it.
2183 JUMP_FUNCTION, NullCallWrapper(), CALL_AS_METHOD); 2149 GenerateJumpFunctionIgnoreReceiver(function);
2184 2150
2185 HandlerFrontendFooter(&miss); 2151 HandlerFrontendFooter(&miss);
2186 2152
2187 // Return the generated code. 2153 // Return the generated code.
2188 return GetCode(type, name); 2154 return GetCode(type, name);
2189 } 2155 }
2190 2156
2191 2157
2192 Handle<Code> CallStubCompiler::CompileMathFloorCall( 2158 Handle<Code> CallStubCompiler::CompileMathFloorCall(
2193 Handle<Object> object, 2159 Handle<Object> object,
(...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after
2268 2234
2269 __ Bind(&smi_result); 2235 __ Bind(&smi_result);
2270 // Tag and return the result. 2236 // Tag and return the result.
2271 __ SmiTag(result, int_value); 2237 __ SmiTag(result, int_value);
2272 2238
2273 __ Bind(&return_result); 2239 __ Bind(&return_result);
2274 __ Drop(argc + 1); 2240 __ Drop(argc + 1);
2275 __ Ret(); 2241 __ Ret();
2276 2242
2277 __ Bind(&slow); 2243 __ Bind(&slow);
2278 // Tail call the full function. We do not have to patch the receiver 2244 // We do not have to patch the receiver because the function makes no use of
2279 // because the function makes no use of it. 2245 // it.
2280 ParameterCount expected(function); 2246 GenerateJumpFunctionIgnoreReceiver(function);
2281 __ InvokeFunction(function, expected, arguments(),
2282 JUMP_FUNCTION, NullCallWrapper(), CALL_AS_METHOD);
2283 2247
2284 HandlerFrontendFooter(&miss); 2248 HandlerFrontendFooter(&miss);
2285 2249
2286 // Return the generated code. 2250 // Return the generated code.
2287 return GetCode(type, name); 2251 return GetCode(type, name);
2288 } 2252 }
2289 2253
2290 2254
2291 Handle<Code> CallStubCompiler::CompileMathAbsCall( 2255 Handle<Code> CallStubCompiler::CompileMathAbsCall(
2292 Handle<Object> object, 2256 Handle<Object> object,
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
2336 __ Ret(); 2300 __ Ret();
2337 2301
2338 __ Bind(&negative_sign); 2302 __ Bind(&negative_sign);
2339 FPRegister double_value = d0; 2303 FPRegister double_value = d0;
2340 __ Fmov(double_value, value); 2304 __ Fmov(double_value, value);
2341 __ Fabs(double_value, double_value); 2305 __ Fabs(double_value, double_value);
2342 __ AllocateHeapNumberWithValue(result, double_value, &slow, x1, x3); 2306 __ AllocateHeapNumberWithValue(result, double_value, &slow, x1, x3);
2343 __ Drop(argc + 1); 2307 __ Drop(argc + 1);
2344 __ Ret(); 2308 __ Ret();
2345 2309
2346 // Tail call the full function. We do not have to patch the receiver
2347 // because the function makes no use of it.
2348 __ Bind(&slow); 2310 __ Bind(&slow);
2349 ParameterCount expected(function); 2311 // We do not have to patch the receiver because the function makes no use of
2350 __ InvokeFunction(function, expected, arguments(), 2312 // it.
2351 JUMP_FUNCTION, NullCallWrapper(), CALL_AS_METHOD); 2313 GenerateJumpFunctionIgnoreReceiver(function);
2352 2314
2353 HandlerFrontendFooter(&miss); 2315 HandlerFrontendFooter(&miss);
2354 2316
2355 // Return the generated code. 2317 // Return the generated code.
2356 return GetCode(type, name); 2318 return GetCode(type, name);
2357 } 2319 }
2358 2320
2359 2321
2360 Handle<Code> CallStubCompiler::CompileFastApiCall( 2322 Handle<Code> CallStubCompiler::CompileFastApiCall(
2361 const CallOptimization& optimization, 2323 const CallOptimization& optimization,
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
2395 2357
2396 // Check that the maps haven't changed and find a Holder as a side effect. 2358 // Check that the maps haven't changed and find a Holder as a side effect.
2397 CheckPrototypes(IC::CurrentTypeOf(object, isolate()), 2359 CheckPrototypes(IC::CurrentTypeOf(object, isolate()),
2398 receiver, holder, x0, x3, x4, name, depth, &miss); 2360 receiver, holder, x0, x3, x4, name, depth, &miss);
2399 2361
2400 GenerateFastApiDirectCall(masm(), optimization, argc, false); 2362 GenerateFastApiDirectCall(masm(), optimization, argc, false);
2401 2363
2402 __ Bind(&miss); 2364 __ Bind(&miss);
2403 FreeSpaceForFastApiCall(masm()); 2365 FreeSpaceForFastApiCall(masm());
2404 2366
2405 __ Bind(&miss_before_stack_reserved); 2367 HandlerFrontendFooter(&miss_before_stack_reserved);
2406 GenerateMissBranch();
2407 2368
2408 // Return the generated code. 2369 // Return the generated code.
2409 return GetCode(function); 2370 return GetCode(function);
2410 } 2371 }
2411 2372
2412 2373
2413 void StubCompiler::GenerateBooleanCheck(Register object, Label* miss) { 2374 void StubCompiler::GenerateBooleanCheck(Register object, Label* miss) {
2414 Label success; 2375 Label success;
2415 // Check that the object is a boolean. 2376 // Check that the object is a boolean.
2416 // TODO(all): Optimize this like LCodeGen::DoDeferredTaggedToI. 2377 // TODO(all): Optimize this like LCodeGen::DoDeferredTaggedToI.
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after
2510 Handle<Object> prototype(object->GetPrototype(isolate()), isolate()); 2471 Handle<Object> prototype(object->GetPrototype(isolate()), isolate());
2511 receiver = CheckPrototypes( 2472 receiver = CheckPrototypes(
2512 IC::CurrentTypeOf(prototype, isolate()), 2473 IC::CurrentTypeOf(prototype, isolate()),
2513 prototype_reg, holder, x1, x3, x4, name, miss); 2474 prototype_reg, holder, x1, x3, x4, name, miss);
2514 } 2475 }
2515 2476
2516 return receiver; 2477 return receiver;
2517 } 2478 }
2518 2479
2519 2480
2520 void CallStubCompiler::CompileHandlerBackend(Handle<JSFunction> function) { 2481 void CallStubCompiler::GenerateJumpFunction(Handle<Object> object,
2521 CallKind call_kind = CallICBase::Contextual::decode(extra_state_) 2482 Register function,
2522 ? CALL_AS_FUNCTION 2483 Label* miss) {
2523 : CALL_AS_METHOD; 2484 ASSERT(function.Is(x1));
2524 ParameterCount expected(function); 2485 // Check that the function really is a function.
2525 __ InvokeFunction(function, expected, arguments(), 2486 GenerateFunctionCheck(function, x3, miss);
2526 JUMP_FUNCTION, NullCallWrapper(), call_kind); 2487 PatchGlobalProxy(object);
2488
2489 // Invoke the function.
2490 __ InvokeFunction(function, arguments(), JUMP_FUNCTION,
2491 NullCallWrapper(), call_kind());
2527 } 2492 }
2528 2493
2529 2494
2530 Handle<Code> CallStubCompiler::CompileCallConstant(
2531 Handle<Object> object,
2532 Handle<JSObject> holder,
2533 Handle<Name> name,
2534 CheckType check,
2535 Handle<JSFunction> function) {
2536 if (HasCustomCallGenerator(function)) {
2537 Handle<Code> code = CompileCustomCall(object, holder,
2538 Handle<Cell>::null(),
2539 function, Handle<String>::cast(name),
2540 Code::FAST);
2541 // A null handle means bail out to the regular compiler code below.
2542 if (!code.is_null()) return code;
2543 }
2544
2545 Label miss;
2546 HandlerFrontendHeader(object, holder, name, check, &miss);
2547 PatchGlobalProxy(object);
2548 CompileHandlerBackend(function);
2549 HandlerFrontendFooter(&miss);
2550
2551 // Return the generated code.
2552 return GetCode(function);
2553 }
2554
2555
2556 Handle<Code> CallStubCompiler::CompileCallInterceptor(Handle<JSObject> object, 2495 Handle<Code> CallStubCompiler::CompileCallInterceptor(Handle<JSObject> object,
2557 Handle<JSObject> holder, 2496 Handle<JSObject> holder,
2558 Handle<Name> name) { 2497 Handle<Name> name) {
2559 Label miss; 2498 Label miss;
2560 Register name_reg = x2; 2499 Register name_reg = x2;
2561 2500
2562 GenerateNameCheck(name, &miss); 2501 GenerateNameCheck(name, &miss);
2563 2502
2564 const int argc = arguments().immediate(); 2503 const int argc = arguments().immediate();
2565 LookupResult lookup(isolate()); 2504 LookupResult lookup(isolate());
2566 LookupPostInterceptor(holder, name, &lookup); 2505 LookupPostInterceptor(holder, name, &lookup);
2567 2506
2568 // Get the receiver from the stack. 2507 // Get the receiver from the stack.
2569 Register receiver = x5; 2508 Register receiver = x5;
2570 __ Peek(receiver, argc * kPointerSize); 2509 __ Peek(receiver, argc * kPointerSize);
2571 2510
2572 CallInterceptorCompiler compiler(this, arguments(), name_reg, extra_state_); 2511 CallInterceptorCompiler compiler(this, arguments(), name_reg, extra_state());
2573 compiler.Compile( 2512 compiler.Compile(
2574 masm(), object, holder, name, &lookup, receiver, x3, x4, x0, &miss); 2513 masm(), object, holder, name, &lookup, receiver, x3, x4, x0, &miss);
2575 2514
2576 // Move returned value, the function to call, to x1 (this is required by 2515 // Move returned value, the function to call, to x1 (this is required by
2577 // GenerateCallFunction). 2516 // GenerateCallFunction).
2578 Register function = x1; 2517 Register function = x1;
2579 __ Mov(function, x0); 2518 __ Mov(function, x0);
2580 2519
2581 // Restore receiver. 2520 // Restore receiver.
2582 __ Peek(receiver, argc * kPointerSize); 2521 __ Peek(receiver, argc * kPointerSize);
2583 2522
2584 GenerateCallFunction( 2523 GenerateJumpFunction(object, x1, &miss);
2585 masm(), object, arguments(), &miss, extra_state_, function, receiver, x3);
2586 2524
2587 // Handle call cache miss. 2525 HandlerFrontendFooter(&miss);
2588 __ Bind(&miss);
2589 GenerateMissBranch();
2590 2526
2591 // Return the generated code. 2527 // Return the generated code.
2592 return GetCode(Code::FAST, name); 2528 return GetCode(Code::FAST, name);
2593 } 2529 }
2594 2530
2595 2531
2596 Handle<Code> CallStubCompiler::CompileCallGlobal( 2532 Handle<Code> CallStubCompiler::CompileCallGlobal(
2597 Handle<JSObject> object, 2533 Handle<JSObject> object,
2598 Handle<GlobalObject> holder, 2534 Handle<GlobalObject> holder,
2599 Handle<PropertyCell> cell, 2535 Handle<PropertyCell> cell,
2600 Handle<JSFunction> function, 2536 Handle<JSFunction> function,
2601 Handle<Name> name) { 2537 Handle<Name> name) {
2602 if (HasCustomCallGenerator(function)) { 2538 if (HasCustomCallGenerator(function)) {
2603 Handle<Code> code = CompileCustomCall( 2539 Handle<Code> code = CompileCustomCall(
2604 object, holder, cell, function, Handle<String>::cast(name), 2540 object, holder, cell, function, Handle<String>::cast(name),
2605 Code::NORMAL); 2541 Code::NORMAL);
2606 // A null handle means bail out to the regular compiler code below. 2542 // A null handle means bail out to the regular compiler code below.
2607 if (!code.is_null()) return code; 2543 if (!code.is_null()) return code;
2608 } 2544 }
2609 2545
2610 Label miss; 2546 Label miss;
2611 HandlerFrontendHeader(object, holder, name, RECEIVER_MAP_CHECK, &miss); 2547 HandlerFrontendHeader(object, holder, name, RECEIVER_MAP_CHECK, &miss);
2548 // Potentially loads a closure that matches the shared function info of the
2549 // function, rather than function.
2612 GenerateLoadFunctionFromCell(cell, function, &miss); 2550 GenerateLoadFunctionFromCell(cell, function, &miss);
2613 // After these two calls the receiver is left in x0 and the function in x1. 2551 // After these two calls the receiver is left in x0 and the function in x1.
2614 Register function_reg = x1; 2552 Register function_reg = x1;
2615 2553
2616 PatchGlobalProxy(object);
2617
2618 // Set up the context.
2619 __ Ldr(cp, FieldMemOperand(function_reg, JSFunction::kContextOffset));
2620
2621 // Jump to the cached code (tail call).
2622 Counters* counters = isolate()->counters(); 2554 Counters* counters = isolate()->counters();
2623 __ IncrementCounter(counters->call_global_inline(), 1, x3, x4); 2555 __ IncrementCounter(counters->call_global_inline(), 1, x3, x4);
2624 ParameterCount expected(function->shared()->formal_parameter_count()); 2556 GenerateJumpFunction(object, function_reg, function);
2625 CallKind call_kind = CallICBase::Contextual::decode(extra_state_)
2626 ? CALL_AS_FUNCTION
2627 : CALL_AS_METHOD;
2628 // We call indirectly through the code field in the function to
2629 // allow recompilation to take effect without changing any of the
2630 // call sites.
2631 __ Ldr(x3, FieldMemOperand(function_reg, JSFunction::kCodeEntryOffset));
2632 __ InvokeCode(
2633 x3, expected, arguments(), JUMP_FUNCTION, NullCallWrapper(), call_kind);
2634
2635 HandlerFrontendFooter(&miss); 2557 HandlerFrontendFooter(&miss);
2636 2558
2637 // Return the generated code. 2559 // Return the generated code.
2638 return GetCode(Code::NORMAL, name); 2560 return GetCode(Code::NORMAL, name);
2639 } 2561 }
2640 2562
2641 2563
2642 Handle<Code> StoreStubCompiler::CompileStoreCallback( 2564 Handle<Code> StoreStubCompiler::CompileStoreCallback(
2643 Handle<JSObject> object, 2565 Handle<JSObject> object,
2644 Handle<JSObject> holder, 2566 Handle<JSObject> holder,
(...skipping 361 matching lines...) Expand 10 before | Expand all | Expand 10 after
3006 2928
3007 // Miss case, call the runtime. 2929 // Miss case, call the runtime.
3008 __ Bind(&miss); 2930 __ Bind(&miss);
3009 TailCallBuiltin(masm, Builtins::kKeyedLoadIC_Miss); 2931 TailCallBuiltin(masm, Builtins::kKeyedLoadIC_Miss);
3010 } 2932 }
3011 2933
3012 2934
3013 } } // namespace v8::internal 2935 } } // namespace v8::internal
3014 2936
3015 #endif // V8_TARGET_ARCH_A64 2937 #endif // V8_TARGET_ARCH_A64
OLDNEW
« no previous file with comments | « src/a64/macro-assembler-a64.cc ('k') | src/allocation-tracker.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698