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

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

Issue 96763002: Reupload CallIC changes. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Addressed comments Created 7 years 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/arm/macro-assembler-arm.cc ('k') | src/ia32/macro-assembler-ia32.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 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 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 724 matching lines...) Expand 10 before | Expand all | Expand 10 after
735 void StoreStubCompiler::GenerateRestoreName(MacroAssembler* masm, 735 void StoreStubCompiler::GenerateRestoreName(MacroAssembler* masm,
736 Label* label, 736 Label* label,
737 Handle<Name> name) { 737 Handle<Name> name) {
738 if (!label->is_unused()) { 738 if (!label->is_unused()) {
739 __ bind(label); 739 __ bind(label);
740 __ mov(this->name(), Operand(name)); 740 __ mov(this->name(), Operand(name));
741 } 741 }
742 } 742 }
743 743
744 744
745 static void GenerateCallFunction(MacroAssembler* masm,
746 Handle<Object> object,
747 const ParameterCount& arguments,
748 Label* miss,
749 ExtraICState extra_ic_state) {
750 // ----------- S t a t e -------------
751 // -- r0: receiver
752 // -- r1: function to call
753 // -----------------------------------
754
755 // Check that the function really is a function.
756 __ JumpIfSmi(r1, miss);
757 __ CompareObjectType(r1, r3, r3, JS_FUNCTION_TYPE);
758 __ b(ne, miss);
759
760 if (object->IsGlobalObject()) {
761 const int argc = arguments.immediate();
762 const int receiver_offset = argc * kPointerSize;
763 __ ldr(r3, FieldMemOperand(r0, GlobalObject::kGlobalReceiverOffset));
764 __ str(r3, MemOperand(sp, receiver_offset));
765 }
766
767 // Invoke the function.
768 CallKind call_kind = CallICBase::Contextual::decode(extra_ic_state)
769 ? CALL_AS_FUNCTION
770 : CALL_AS_METHOD;
771 __ InvokeFunction(r1, arguments, JUMP_FUNCTION, NullCallWrapper(), call_kind);
772 }
773
774
775 static void PushInterceptorArguments(MacroAssembler* masm, 745 static void PushInterceptorArguments(MacroAssembler* masm,
776 Register receiver, 746 Register receiver,
777 Register holder, 747 Register holder,
778 Register name, 748 Register name,
779 Handle<JSObject> holder_obj) { 749 Handle<JSObject> holder_obj) {
780 STATIC_ASSERT(StubCache::kInterceptorArgsNameIndex == 0); 750 STATIC_ASSERT(StubCache::kInterceptorArgsNameIndex == 0);
781 STATIC_ASSERT(StubCache::kInterceptorArgsInfoIndex == 1); 751 STATIC_ASSERT(StubCache::kInterceptorArgsInfoIndex == 1);
782 STATIC_ASSERT(StubCache::kInterceptorArgsThisIndex == 2); 752 STATIC_ASSERT(StubCache::kInterceptorArgsThisIndex == 2);
783 STATIC_ASSERT(StubCache::kInterceptorArgsHolderIndex == 3); 753 STATIC_ASSERT(StubCache::kInterceptorArgsHolderIndex == 3);
784 STATIC_ASSERT(StubCache::kInterceptorArgsLength == 4); 754 STATIC_ASSERT(StubCache::kInterceptorArgsLength == 4);
(...skipping 163 matching lines...) Expand 10 before | Expand all | Expand 10 after
948 ASSERT(!scratch.is(values[i])); 918 ASSERT(!scratch.is(values[i]));
949 __ str(receiver, MemOperand(sp, index-- * kPointerSize)); 919 __ str(receiver, MemOperand(sp, index-- * kPointerSize));
950 } 920 }
951 921
952 GenerateFastApiDirectCall(masm, optimization, argc, true); 922 GenerateFastApiDirectCall(masm, optimization, argc, true);
953 } 923 }
954 924
955 925
956 class CallInterceptorCompiler BASE_EMBEDDED { 926 class CallInterceptorCompiler BASE_EMBEDDED {
957 public: 927 public:
958 CallInterceptorCompiler(StubCompiler* stub_compiler, 928 CallInterceptorCompiler(CallStubCompiler* stub_compiler,
959 const ParameterCount& arguments, 929 const ParameterCount& arguments,
960 Register name, 930 Register name,
961 ExtraICState extra_ic_state) 931 ExtraICState extra_ic_state)
962 : stub_compiler_(stub_compiler), 932 : stub_compiler_(stub_compiler),
963 arguments_(arguments), 933 arguments_(arguments),
964 name_(name), 934 name_(name),
965 extra_ic_state_(extra_ic_state) {} 935 extra_ic_state_(extra_ic_state) {}
966 936
967 void Compile(MacroAssembler* masm, 937 void Compile(MacroAssembler* masm,
968 Handle<JSObject> object, 938 Handle<JSObject> object,
(...skipping 91 matching lines...) Expand 10 before | Expand all | Expand 10 after
1060 // safe to omit it here, as if present, it should be fetched 1030 // safe to omit it here, as if present, it should be fetched
1061 // by the previous CheckPrototypes. 1031 // by the previous CheckPrototypes.
1062 ASSERT(depth2 == kInvalidProtoDepth); 1032 ASSERT(depth2 == kInvalidProtoDepth);
1063 } 1033 }
1064 1034
1065 // Invoke function. 1035 // Invoke function.
1066 if (can_do_fast_api_call) { 1036 if (can_do_fast_api_call) {
1067 GenerateFastApiDirectCall( 1037 GenerateFastApiDirectCall(
1068 masm, optimization, arguments_.immediate(), false); 1038 masm, optimization, arguments_.immediate(), false);
1069 } else { 1039 } else {
1070 CallKind call_kind = CallICBase::Contextual::decode(extra_ic_state_)
1071 ? CALL_AS_FUNCTION
1072 : CALL_AS_METHOD;
1073 Handle<JSFunction> function = optimization.constant_function(); 1040 Handle<JSFunction> function = optimization.constant_function();
1074 ParameterCount expected(function); 1041 stub_compiler_->GenerateJumpFunctionIgnoreReceiver(function);
1075 __ InvokeFunction(function, expected, arguments_,
1076 JUMP_FUNCTION, NullCallWrapper(), call_kind);
1077 } 1042 }
1078 1043
1079 // Deferred code for fast API call case---clean preallocated space. 1044 // Deferred code for fast API call case---clean preallocated space.
1080 if (can_do_fast_api_call) { 1045 if (can_do_fast_api_call) {
1081 __ bind(&miss_cleanup); 1046 __ bind(&miss_cleanup);
1082 FreeSpaceForFastApiCall(masm); 1047 FreeSpaceForFastApiCall(masm);
1083 __ b(miss_label); 1048 __ b(miss_label);
1084 } 1049 }
1085 1050
1086 // Invoke a regular function. 1051 // Invoke a regular function.
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
1132 IC::kLoadPropertyWithInterceptorOnly); 1097 IC::kLoadPropertyWithInterceptorOnly);
1133 __ pop(name_); // Restore the name. 1098 __ pop(name_); // Restore the name.
1134 __ pop(receiver); // Restore the holder. 1099 __ pop(receiver); // Restore the holder.
1135 } 1100 }
1136 // If interceptor returns no-result sentinel, call the constant function. 1101 // If interceptor returns no-result sentinel, call the constant function.
1137 __ LoadRoot(scratch, Heap::kNoInterceptorResultSentinelRootIndex); 1102 __ LoadRoot(scratch, Heap::kNoInterceptorResultSentinelRootIndex);
1138 __ cmp(r0, scratch); 1103 __ cmp(r0, scratch);
1139 __ b(ne, interceptor_succeeded); 1104 __ b(ne, interceptor_succeeded);
1140 } 1105 }
1141 1106
1142 StubCompiler* stub_compiler_; 1107 CallStubCompiler* stub_compiler_;
1143 const ParameterCount& arguments_; 1108 const ParameterCount& arguments_;
1144 Register name_; 1109 Register name_;
1145 ExtraICState extra_ic_state_; 1110 ExtraICState extra_ic_state_;
1146 }; 1111 };
1147 1112
1148 1113
1149 void StubCompiler::GenerateTailCall(MacroAssembler* masm, Handle<Code> code) { 1114 void StubCompiler::GenerateTailCall(MacroAssembler* masm, Handle<Code> code) {
1150 __ Jump(code, RelocInfo::CODE_TARGET); 1115 __ Jump(code, RelocInfo::CODE_TARGET);
1151 } 1116 }
1152 1117
(...skipping 381 matching lines...) Expand 10 before | Expand all | Expand 10 after
1534 1499
1535 1500
1536 void CallStubCompiler::GenerateNameCheck(Handle<Name> name, Label* miss) { 1501 void CallStubCompiler::GenerateNameCheck(Handle<Name> name, Label* miss) {
1537 if (kind_ == Code::KEYED_CALL_IC) { 1502 if (kind_ == Code::KEYED_CALL_IC) {
1538 __ cmp(r2, Operand(name)); 1503 __ cmp(r2, Operand(name));
1539 __ b(ne, miss); 1504 __ b(ne, miss);
1540 } 1505 }
1541 } 1506 }
1542 1507
1543 1508
1509 void CallStubCompiler::GenerateFunctionCheck(Register function,
1510 Register scratch,
1511 Label* miss) {
1512 __ JumpIfSmi(function, miss);
1513 __ CompareObjectType(function, scratch, scratch, JS_FUNCTION_TYPE);
1514 __ b(ne, miss);
1515 }
1516
1517
1544 void CallStubCompiler::GenerateLoadFunctionFromCell( 1518 void CallStubCompiler::GenerateLoadFunctionFromCell(
1545 Handle<Cell> cell, 1519 Handle<Cell> cell,
1546 Handle<JSFunction> function, 1520 Handle<JSFunction> function,
1547 Label* miss) { 1521 Label* miss) {
1548 // Get the value from the cell. 1522 // Get the value from the cell.
1549 __ mov(r3, Operand(cell)); 1523 __ mov(r3, Operand(cell));
1550 __ ldr(r1, FieldMemOperand(r3, Cell::kValueOffset)); 1524 __ ldr(r1, FieldMemOperand(r3, Cell::kValueOffset));
1551 1525
1552 // Check that the cell contains the same function. 1526 // Check that the cell contains the same function.
1553 if (heap()->InNewSpace(*function)) { 1527 if (heap()->InNewSpace(*function)) {
1554 // We can't embed a pointer to a function in new space so we have 1528 // We can't embed a pointer to a function in new space so we have
1555 // to verify that the shared function info is unchanged. This has 1529 // to verify that the shared function info is unchanged. This has
1556 // the nice side effect that multiple closures based on the same 1530 // the nice side effect that multiple closures based on the same
1557 // function can all use this call IC. Before we load through the 1531 // function can all use this call IC. Before we load through the
1558 // function, we have to verify that it still is a function. 1532 // function, we have to verify that it still is a function.
1559 __ JumpIfSmi(r1, miss); 1533 GenerateFunctionCheck(r1, r3, miss);
1560 __ CompareObjectType(r1, r3, r3, JS_FUNCTION_TYPE);
1561 __ b(ne, miss);
1562 1534
1563 // Check the shared function info. Make sure it hasn't changed. 1535 // Check the shared function info. Make sure it hasn't changed.
1564 __ Move(r3, Handle<SharedFunctionInfo>(function->shared())); 1536 __ Move(r3, Handle<SharedFunctionInfo>(function->shared()));
1565 __ ldr(r4, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset)); 1537 __ ldr(r4, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset));
1566 __ cmp(r4, r3); 1538 __ cmp(r4, r3);
1567 } else { 1539 } else {
1568 __ cmp(r1, Operand(function)); 1540 __ cmp(r1, Operand(function));
1569 } 1541 }
1570 __ b(ne, miss); 1542 __ b(ne, miss);
1571 } 1543 }
(...skipping 11 matching lines...) Expand all
1583 Handle<Code> CallStubCompiler::CompileCallField(Handle<JSObject> object, 1555 Handle<Code> CallStubCompiler::CompileCallField(Handle<JSObject> object,
1584 Handle<JSObject> holder, 1556 Handle<JSObject> holder,
1585 PropertyIndex index, 1557 PropertyIndex index,
1586 Handle<Name> name) { 1558 Handle<Name> name) {
1587 Label miss; 1559 Label miss;
1588 1560
1589 Register reg = HandlerFrontendHeader( 1561 Register reg = HandlerFrontendHeader(
1590 object, holder, name, RECEIVER_MAP_CHECK, &miss); 1562 object, holder, name, RECEIVER_MAP_CHECK, &miss);
1591 GenerateFastPropertyLoad(masm(), r1, reg, index.is_inobject(holder), 1563 GenerateFastPropertyLoad(masm(), r1, reg, index.is_inobject(holder),
1592 index.translate(holder), Representation::Tagged()); 1564 index.translate(holder), Representation::Tagged());
1593 1565 GenerateJumpFunction(object, r1, &miss);
1594 GenerateCallFunction(masm(), object, arguments(), &miss, extra_state_);
1595 1566
1596 HandlerFrontendFooter(&miss); 1567 HandlerFrontendFooter(&miss);
1597 1568
1598 // Return the generated code. 1569 // Return the generated code.
1599 return GetCode(Code::FAST, name); 1570 return GetCode(Code::FAST, name);
1600 } 1571 }
1601 1572
1602 1573
1603 Handle<Code> CallStubCompiler::CompileArrayCodeCall( 1574 Handle<Code> CallStubCompiler::CompileArrayCodeCall(
1604 Handle<Object> object, 1575 Handle<Object> object,
(...skipping 394 matching lines...) Expand 10 before | Expand all | Expand 10 after
1999 if (index_out_of_range.is_linked()) { 1970 if (index_out_of_range.is_linked()) {
2000 __ bind(&index_out_of_range); 1971 __ bind(&index_out_of_range);
2001 __ LoadRoot(r0, Heap::kNanValueRootIndex); 1972 __ LoadRoot(r0, Heap::kNanValueRootIndex);
2002 __ Drop(argc + 1); 1973 __ Drop(argc + 1);
2003 __ Ret(); 1974 __ Ret();
2004 } 1975 }
2005 1976
2006 __ bind(&miss); 1977 __ bind(&miss);
2007 // Restore function name in r2. 1978 // Restore function name in r2.
2008 __ Move(r2, name); 1979 __ Move(r2, name);
2009 __ bind(&name_miss); 1980 HandlerFrontendFooter(&name_miss);
2010 GenerateMissBranch();
2011 1981
2012 // Return the generated code. 1982 // Return the generated code.
2013 return GetCode(type, name); 1983 return GetCode(type, name);
2014 } 1984 }
2015 1985
2016 1986
2017 Handle<Code> CallStubCompiler::CompileStringCharAtCall( 1987 Handle<Code> CallStubCompiler::CompileStringCharAtCall(
2018 Handle<Object> object, 1988 Handle<Object> object,
2019 Handle<JSObject> holder, 1989 Handle<JSObject> holder,
2020 Handle<Cell> cell, 1990 Handle<Cell> cell,
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
2066 if (index_out_of_range.is_linked()) { 2036 if (index_out_of_range.is_linked()) {
2067 __ bind(&index_out_of_range); 2037 __ bind(&index_out_of_range);
2068 __ LoadRoot(r0, Heap::kempty_stringRootIndex); 2038 __ LoadRoot(r0, Heap::kempty_stringRootIndex);
2069 __ Drop(argc + 1); 2039 __ Drop(argc + 1);
2070 __ Ret(); 2040 __ Ret();
2071 } 2041 }
2072 2042
2073 __ bind(&miss); 2043 __ bind(&miss);
2074 // Restore function name in r2. 2044 // Restore function name in r2.
2075 __ Move(r2, name); 2045 __ Move(r2, name);
2076 __ bind(&name_miss); 2046 HandlerFrontendFooter(&name_miss);
2077 GenerateMissBranch();
2078 2047
2079 // Return the generated code. 2048 // Return the generated code.
2080 return GetCode(type, name); 2049 return GetCode(type, name);
2081 } 2050 }
2082 2051
2083 2052
2084 Handle<Code> CallStubCompiler::CompileStringFromCharCodeCall( 2053 Handle<Code> CallStubCompiler::CompileStringFromCharCodeCall(
2085 Handle<Object> object, 2054 Handle<Object> object,
2086 Handle<JSObject> holder, 2055 Handle<JSObject> holder,
2087 Handle<Cell> cell, 2056 Handle<Cell> cell,
(...skipping 26 matching lines...) Expand all
2114 __ and_(code, code, Operand(Smi::FromInt(0xffff))); 2083 __ and_(code, code, Operand(Smi::FromInt(0xffff)));
2115 2084
2116 StringCharFromCodeGenerator generator(code, r0); 2085 StringCharFromCodeGenerator generator(code, r0);
2117 generator.GenerateFast(masm()); 2086 generator.GenerateFast(masm());
2118 __ Drop(argc + 1); 2087 __ Drop(argc + 1);
2119 __ Ret(); 2088 __ Ret();
2120 2089
2121 StubRuntimeCallHelper call_helper; 2090 StubRuntimeCallHelper call_helper;
2122 generator.GenerateSlow(masm(), call_helper); 2091 generator.GenerateSlow(masm(), call_helper);
2123 2092
2124 // Tail call the full function. We do not have to patch the receiver
2125 // because the function makes no use of it.
2126 __ bind(&slow); 2093 __ bind(&slow);
2127 ParameterCount expected(function); 2094 // We do not have to patch the receiver because the function makes no use of
2128 __ InvokeFunction(function, expected, arguments(), 2095 // it.
2129 JUMP_FUNCTION, NullCallWrapper(), CALL_AS_METHOD); 2096 GenerateJumpFunctionIgnoreReceiver(function);
2130 2097
2131 HandlerFrontendFooter(&miss); 2098 HandlerFrontendFooter(&miss);
2132 2099
2133 // Return the generated code. 2100 // Return the generated code.
2134 return GetCode(type, name); 2101 return GetCode(type, name);
2135 } 2102 }
2136 2103
2137 2104
2138 Handle<Code> CallStubCompiler::CompileMathFloorCall( 2105 Handle<Code> CallStubCompiler::CompileMathFloorCall(
2139 Handle<Object> object, 2106 Handle<Object> object,
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after
2207 // the result is either 0x80000000 or 0x7FFFFFFF and won't fit into an smi. 2174 // the result is either 0x80000000 or 0x7FFFFFFF and won't fit into an smi.
2208 // If result doesn't fit into an smi, branch to slow. 2175 // If result doesn't fit into an smi, branch to slow.
2209 __ SmiTag(r0, SetCC); 2176 __ SmiTag(r0, SetCC);
2210 __ b(vs, &slow); 2177 __ b(vs, &slow);
2211 2178
2212 __ bind(&just_return); 2179 __ bind(&just_return);
2213 __ Drop(argc + 1); 2180 __ Drop(argc + 1);
2214 __ Ret(); 2181 __ Ret();
2215 2182
2216 __ bind(&slow); 2183 __ bind(&slow);
2217 // Tail call the full function. We do not have to patch the receiver 2184 // We do not have to patch the receiver because the function makes no use of
2218 // because the function makes no use of it. 2185 // it.
2219 ParameterCount expected(function); 2186 GenerateJumpFunctionIgnoreReceiver(function);
2220 __ InvokeFunction(function, expected, arguments(),
2221 JUMP_FUNCTION, NullCallWrapper(), CALL_AS_METHOD);
2222 2187
2223 HandlerFrontendFooter(&miss); 2188 HandlerFrontendFooter(&miss);
2224 2189
2225 // Return the generated code. 2190 // Return the generated code.
2226 return GetCode(type, name); 2191 return GetCode(type, name);
2227 } 2192 }
2228 2193
2229 2194
2230 Handle<Code> CallStubCompiler::CompileMathAbsCall( 2195 Handle<Code> CallStubCompiler::CompileMathAbsCall(
2231 Handle<Object> object, 2196 Handle<Object> object,
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
2289 __ bind(&negative_sign); 2254 __ bind(&negative_sign);
2290 __ eor(r1, r1, Operand(HeapNumber::kSignMask)); 2255 __ eor(r1, r1, Operand(HeapNumber::kSignMask));
2291 __ ldr(r3, FieldMemOperand(r0, HeapNumber::kMantissaOffset)); 2256 __ ldr(r3, FieldMemOperand(r0, HeapNumber::kMantissaOffset));
2292 __ LoadRoot(r6, Heap::kHeapNumberMapRootIndex); 2257 __ LoadRoot(r6, Heap::kHeapNumberMapRootIndex);
2293 __ AllocateHeapNumber(r0, r4, r5, r6, &slow); 2258 __ AllocateHeapNumber(r0, r4, r5, r6, &slow);
2294 __ str(r1, FieldMemOperand(r0, HeapNumber::kExponentOffset)); 2259 __ str(r1, FieldMemOperand(r0, HeapNumber::kExponentOffset));
2295 __ str(r3, FieldMemOperand(r0, HeapNumber::kMantissaOffset)); 2260 __ str(r3, FieldMemOperand(r0, HeapNumber::kMantissaOffset));
2296 __ Drop(argc + 1); 2261 __ Drop(argc + 1);
2297 __ Ret(); 2262 __ Ret();
2298 2263
2299 // Tail call the full function. We do not have to patch the receiver
2300 // because the function makes no use of it.
2301 __ bind(&slow); 2264 __ bind(&slow);
2302 ParameterCount expected(function); 2265 // We do not have to patch the receiver because the function makes no use of
2303 __ InvokeFunction(function, expected, arguments(), 2266 // it.
2304 JUMP_FUNCTION, NullCallWrapper(), CALL_AS_METHOD); 2267 GenerateJumpFunctionIgnoreReceiver(function);
2305 2268
2306 HandlerFrontendFooter(&miss); 2269 HandlerFrontendFooter(&miss);
2307 2270
2308 // Return the generated code. 2271 // Return the generated code.
2309 return GetCode(type, name); 2272 return GetCode(type, name);
2310 } 2273 }
2311 2274
2312 2275
2313 Handle<Code> CallStubCompiler::CompileFastApiCall( 2276 Handle<Code> CallStubCompiler::CompileFastApiCall(
2314 const CallOptimization& optimization, 2277 const CallOptimization& optimization,
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
2347 // Check that the maps haven't changed and find a Holder as a side effect. 2310 // Check that the maps haven't changed and find a Holder as a side effect.
2348 CheckPrototypes( 2311 CheckPrototypes(
2349 IC::CurrentTypeOf(object, isolate()), 2312 IC::CurrentTypeOf(object, isolate()),
2350 r1, holder, r0, r3, r4, name, depth, &miss); 2313 r1, holder, r0, r3, r4, name, depth, &miss);
2351 2314
2352 GenerateFastApiDirectCall(masm(), optimization, argc, false); 2315 GenerateFastApiDirectCall(masm(), optimization, argc, false);
2353 2316
2354 __ bind(&miss); 2317 __ bind(&miss);
2355 FreeSpaceForFastApiCall(masm()); 2318 FreeSpaceForFastApiCall(masm());
2356 2319
2357 __ bind(&miss_before_stack_reserved); 2320 HandlerFrontendFooter(&miss_before_stack_reserved);
2358 GenerateMissBranch();
2359 2321
2360 // Return the generated code. 2322 // Return the generated code.
2361 return GetCode(function); 2323 return GetCode(function);
2362 } 2324 }
2363 2325
2364 2326
2365 void StubCompiler::GenerateBooleanCheck(Register object, Label* miss) { 2327 void StubCompiler::GenerateBooleanCheck(Register object, Label* miss) {
2366 Label success; 2328 Label success;
2367 // Check that the object is a boolean. 2329 // Check that the object is a boolean.
2368 __ LoadRoot(ip, Heap::kTrueValueRootIndex); 2330 __ LoadRoot(ip, Heap::kTrueValueRootIndex);
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after
2465 Handle<Object> prototype(object->GetPrototype(isolate()), isolate()); 2427 Handle<Object> prototype(object->GetPrototype(isolate()), isolate());
2466 reg = CheckPrototypes( 2428 reg = CheckPrototypes(
2467 IC::CurrentTypeOf(prototype, isolate()), 2429 IC::CurrentTypeOf(prototype, isolate()),
2468 r1, holder, r1, r3, r4, name, miss); 2430 r1, holder, r1, r3, r4, name, miss);
2469 } 2431 }
2470 2432
2471 return reg; 2433 return reg;
2472 } 2434 }
2473 2435
2474 2436
2475 void CallStubCompiler::CompileHandlerBackend(Handle<JSFunction> function) { 2437 void CallStubCompiler::GenerateJumpFunction(Handle<Object> object,
2476 CallKind call_kind = CallICBase::Contextual::decode(extra_state_) 2438 Register function,
2477 ? CALL_AS_FUNCTION 2439 Label* miss) {
2478 : CALL_AS_METHOD; 2440 ASSERT(function.is(r1));
2479 ParameterCount expected(function); 2441 // Check that the function really is a function.
2480 __ InvokeFunction(function, expected, arguments(), 2442 GenerateFunctionCheck(function, r3, miss);
2481 JUMP_FUNCTION, NullCallWrapper(), call_kind); 2443 PatchGlobalProxy(object);
2444
2445 // Invoke the function.
2446 __ InvokeFunction(r1, arguments(), JUMP_FUNCTION,
2447 NullCallWrapper(), call_kind());
2482 } 2448 }
2483 2449
2484 2450
2485 Handle<Code> CallStubCompiler::CompileCallConstant(
2486 Handle<Object> object,
2487 Handle<JSObject> holder,
2488 Handle<Name> name,
2489 CheckType check,
2490 Handle<JSFunction> function) {
2491 if (HasCustomCallGenerator(function)) {
2492 Handle<Code> code = CompileCustomCall(object, holder,
2493 Handle<Cell>::null(),
2494 function, Handle<String>::cast(name),
2495 Code::FAST);
2496 // A null handle means bail out to the regular compiler code below.
2497 if (!code.is_null()) return code;
2498 }
2499
2500 Label miss;
2501 HandlerFrontendHeader(object, holder, name, check, &miss);
2502 PatchGlobalProxy(object);
2503 CompileHandlerBackend(function);
2504 HandlerFrontendFooter(&miss);
2505
2506 // Return the generated code.
2507 return GetCode(function);
2508 }
2509
2510
2511 Handle<Code> CallStubCompiler::CompileCallInterceptor(Handle<JSObject> object, 2451 Handle<Code> CallStubCompiler::CompileCallInterceptor(Handle<JSObject> object,
2512 Handle<JSObject> holder, 2452 Handle<JSObject> holder,
2513 Handle<Name> name) { 2453 Handle<Name> name) {
2514 Label miss; 2454 Label miss;
2515 GenerateNameCheck(name, &miss); 2455 GenerateNameCheck(name, &miss);
2516 2456
2517 // Get the number of arguments. 2457 // Get the number of arguments.
2518 const int argc = arguments().immediate(); 2458 const int argc = arguments().immediate();
2519 LookupResult lookup(isolate()); 2459 LookupResult lookup(isolate());
2520 LookupPostInterceptor(holder, name, &lookup); 2460 LookupPostInterceptor(holder, name, &lookup);
2521 2461
2522 // Get the receiver from the stack. 2462 // Get the receiver from the stack.
2523 __ ldr(r1, MemOperand(sp, argc * kPointerSize)); 2463 __ ldr(r1, MemOperand(sp, argc * kPointerSize));
2524 2464
2525 CallInterceptorCompiler compiler(this, arguments(), r2, extra_state_); 2465 CallInterceptorCompiler compiler(this, arguments(), r2, extra_state_);
2526 compiler.Compile(masm(), object, holder, name, &lookup, r1, r3, r4, r0, 2466 compiler.Compile(masm(), object, holder, name, &lookup, r1, r3, r4, r0,
2527 &miss); 2467 &miss);
2528 2468
2529 // Move returned value, the function to call, to r1. 2469 // Move returned value, the function to call, to r1.
2530 __ mov(r1, r0); 2470 __ mov(r1, r0);
2531 // Restore receiver. 2471 // Restore receiver.
2532 __ ldr(r0, MemOperand(sp, argc * kPointerSize)); 2472 __ ldr(r0, MemOperand(sp, argc * kPointerSize));
2533 2473
2534 GenerateCallFunction(masm(), object, arguments(), &miss, extra_state_); 2474 GenerateJumpFunction(object, r1, &miss);
2535 2475
2536 // Handle call cache miss. 2476 HandlerFrontendFooter(&miss);
2537 __ bind(&miss);
2538 GenerateMissBranch();
2539 2477
2540 // Return the generated code. 2478 // Return the generated code.
2541 return GetCode(Code::FAST, name); 2479 return GetCode(Code::FAST, name);
2542 } 2480 }
2543 2481
2544 2482
2545 Handle<Code> CallStubCompiler::CompileCallGlobal( 2483 Handle<Code> CallStubCompiler::CompileCallGlobal(
2546 Handle<JSObject> object, 2484 Handle<JSObject> object,
2547 Handle<GlobalObject> holder, 2485 Handle<GlobalObject> holder,
2548 Handle<PropertyCell> cell, 2486 Handle<PropertyCell> cell,
2549 Handle<JSFunction> function, 2487 Handle<JSFunction> function,
2550 Handle<Name> name) { 2488 Handle<Name> name) {
2551 if (HasCustomCallGenerator(function)) { 2489 if (HasCustomCallGenerator(function)) {
2552 Handle<Code> code = CompileCustomCall( 2490 Handle<Code> code = CompileCustomCall(
2553 object, holder, cell, function, Handle<String>::cast(name), 2491 object, holder, cell, function, Handle<String>::cast(name),
2554 Code::NORMAL); 2492 Code::NORMAL);
2555 // A null handle means bail out to the regular compiler code below. 2493 // A null handle means bail out to the regular compiler code below.
2556 if (!code.is_null()) return code; 2494 if (!code.is_null()) return code;
2557 } 2495 }
2558 2496
2559 Label miss; 2497 Label miss;
2560 HandlerFrontendHeader(object, holder, name, RECEIVER_MAP_CHECK, &miss); 2498 HandlerFrontendHeader(object, holder, name, RECEIVER_MAP_CHECK, &miss);
2499 // Potentially loads a closure that matches the shared function info of the
2500 // function, rather than function.
2561 GenerateLoadFunctionFromCell(cell, function, &miss); 2501 GenerateLoadFunctionFromCell(cell, function, &miss);
2562 PatchGlobalProxy(object);
2563 2502
2564 // Set up the context (function already in r1).
2565 __ ldr(cp, FieldMemOperand(r1, JSFunction::kContextOffset));
2566
2567 // Jump to the cached code (tail call).
2568 Counters* counters = isolate()->counters(); 2503 Counters* counters = isolate()->counters();
2569 __ IncrementCounter(counters->call_global_inline(), 1, r3, r4); 2504 __ IncrementCounter(counters->call_global_inline(), 1, r3, r4);
2570 ParameterCount expected(function->shared()->formal_parameter_count()); 2505 GenerateJumpFunction(object, r1, function);
2571 CallKind call_kind = CallICBase::Contextual::decode(extra_state_)
2572 ? CALL_AS_FUNCTION
2573 : CALL_AS_METHOD;
2574 // We call indirectly through the code field in the function to
2575 // allow recompilation to take effect without changing any of the
2576 // call sites.
2577 __ ldr(r3, FieldMemOperand(r1, JSFunction::kCodeEntryOffset));
2578 __ InvokeCode(r3, expected, arguments(), JUMP_FUNCTION,
2579 NullCallWrapper(), call_kind);
2580
2581 HandlerFrontendFooter(&miss); 2506 HandlerFrontendFooter(&miss);
2582 2507
2583 // Return the generated code. 2508 // Return the generated code.
2584 return GetCode(Code::NORMAL, name); 2509 return GetCode(Code::NORMAL, name);
2585 } 2510 }
2586 2511
2587 2512
2588 Handle<Code> StoreStubCompiler::CompileStoreCallback( 2513 Handle<Code> StoreStubCompiler::CompileStoreCallback(
2589 Handle<JSObject> object, 2514 Handle<JSObject> object,
2590 Handle<JSObject> holder, 2515 Handle<JSObject> holder,
(...skipping 371 matching lines...) Expand 10 before | Expand all | Expand 10 after
2962 // ----------------------------------- 2887 // -----------------------------------
2963 TailCallBuiltin(masm, Builtins::kKeyedLoadIC_Miss); 2888 TailCallBuiltin(masm, Builtins::kKeyedLoadIC_Miss);
2964 } 2889 }
2965 2890
2966 2891
2967 #undef __ 2892 #undef __
2968 2893
2969 } } // namespace v8::internal 2894 } } // namespace v8::internal
2970 2895
2971 #endif // V8_TARGET_ARCH_ARM 2896 #endif // V8_TARGET_ARCH_ARM
OLDNEW
« no previous file with comments | « src/arm/macro-assembler-arm.cc ('k') | src/ia32/macro-assembler-ia32.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698