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

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

Issue 96053002: MIPS: Cleanup in the CallStubCompiler. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: 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/mips/macro-assembler-mips.cc ('k') | no next file » | 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 714 matching lines...) Expand 10 before | Expand all | Expand 10 after
725 void StoreStubCompiler::GenerateRestoreName(MacroAssembler* masm, 725 void StoreStubCompiler::GenerateRestoreName(MacroAssembler* masm,
726 Label* label, 726 Label* label,
727 Handle<Name> name) { 727 Handle<Name> name) {
728 if (!label->is_unused()) { 728 if (!label->is_unused()) {
729 __ bind(label); 729 __ bind(label);
730 __ li(this->name(), Operand(name)); 730 __ li(this->name(), Operand(name));
731 } 731 }
732 } 732 }
733 733
734 734
735 static void GenerateCallFunction(MacroAssembler* masm,
736 Handle<Object> object,
737 const ParameterCount& arguments,
738 Label* miss,
739 ExtraICState extra_ic_state) {
740 // ----------- S t a t e -------------
741 // -- a0: receiver
742 // -- a1: function to call
743 // -----------------------------------
744 // Check that the function really is a function.
745 __ JumpIfSmi(a1, miss);
746 __ GetObjectType(a1, a3, a3);
747 __ Branch(miss, ne, a3, Operand(JS_FUNCTION_TYPE));
748
749 if (object->IsGlobalObject()) {
750 const int argc = arguments.immediate();
751 const int receiver_offset = argc * kPointerSize;
752 __ lw(a3, FieldMemOperand(a0, GlobalObject::kGlobalReceiverOffset));
753 __ sw(a3, MemOperand(sp, receiver_offset));
754 }
755
756 // Invoke the function.
757 CallKind call_kind = CallICBase::Contextual::decode(extra_ic_state)
758 ? CALL_AS_FUNCTION
759 : CALL_AS_METHOD;
760 __ InvokeFunction(a1, arguments, JUMP_FUNCTION, NullCallWrapper(), call_kind);
761 }
762
763
764 static void PushInterceptorArguments(MacroAssembler* masm, 735 static void PushInterceptorArguments(MacroAssembler* masm,
765 Register receiver, 736 Register receiver,
766 Register holder, 737 Register holder,
767 Register name, 738 Register name,
768 Handle<JSObject> holder_obj) { 739 Handle<JSObject> holder_obj) {
769 STATIC_ASSERT(StubCache::kInterceptorArgsNameIndex == 0); 740 STATIC_ASSERT(StubCache::kInterceptorArgsNameIndex == 0);
770 STATIC_ASSERT(StubCache::kInterceptorArgsInfoIndex == 1); 741 STATIC_ASSERT(StubCache::kInterceptorArgsInfoIndex == 1);
771 STATIC_ASSERT(StubCache::kInterceptorArgsThisIndex == 2); 742 STATIC_ASSERT(StubCache::kInterceptorArgsThisIndex == 2);
772 STATIC_ASSERT(StubCache::kInterceptorArgsHolderIndex == 3); 743 STATIC_ASSERT(StubCache::kInterceptorArgsHolderIndex == 3);
773 STATIC_ASSERT(StubCache::kInterceptorArgsLength == 4); 744 STATIC_ASSERT(StubCache::kInterceptorArgsLength == 4);
(...skipping 161 matching lines...) Expand 10 before | Expand all | Expand 10 after
935 ASSERT(!scratch.is(values[i])); 906 ASSERT(!scratch.is(values[i]));
936 __ sw(receiver, MemOperand(sp, index-- * kPointerSize)); 907 __ sw(receiver, MemOperand(sp, index-- * kPointerSize));
937 } 908 }
938 909
939 GenerateFastApiDirectCall(masm, optimization, argc, true); 910 GenerateFastApiDirectCall(masm, optimization, argc, true);
940 } 911 }
941 912
942 913
943 class CallInterceptorCompiler BASE_EMBEDDED { 914 class CallInterceptorCompiler BASE_EMBEDDED {
944 public: 915 public:
945 CallInterceptorCompiler(StubCompiler* stub_compiler, 916 CallInterceptorCompiler(CallStubCompiler* stub_compiler,
946 const ParameterCount& arguments, 917 const ParameterCount& arguments,
947 Register name, 918 Register name,
948 ExtraICState extra_ic_state) 919 ExtraICState extra_ic_state)
949 : stub_compiler_(stub_compiler), 920 : stub_compiler_(stub_compiler),
950 arguments_(arguments), 921 arguments_(arguments),
951 name_(name), 922 name_(name),
952 extra_ic_state_(extra_ic_state) {} 923 extra_ic_state_(extra_ic_state) {}
953 924
954 void Compile(MacroAssembler* masm, 925 void Compile(MacroAssembler* masm,
955 Handle<JSObject> object, 926 Handle<JSObject> object,
(...skipping 91 matching lines...) Expand 10 before | Expand all | Expand 10 after
1047 // safe to omit it here, as if present, it should be fetched 1018 // safe to omit it here, as if present, it should be fetched
1048 // by the previous CheckPrototypes. 1019 // by the previous CheckPrototypes.
1049 ASSERT(depth2 == kInvalidProtoDepth); 1020 ASSERT(depth2 == kInvalidProtoDepth);
1050 } 1021 }
1051 1022
1052 // Invoke function. 1023 // Invoke function.
1053 if (can_do_fast_api_call) { 1024 if (can_do_fast_api_call) {
1054 GenerateFastApiDirectCall( 1025 GenerateFastApiDirectCall(
1055 masm, optimization, arguments_.immediate(), false); 1026 masm, optimization, arguments_.immediate(), false);
1056 } else { 1027 } else {
1057 CallKind call_kind = CallICBase::Contextual::decode(extra_ic_state_)
1058 ? CALL_AS_FUNCTION
1059 : CALL_AS_METHOD;
1060 Handle<JSFunction> function = optimization.constant_function(); 1028 Handle<JSFunction> function = optimization.constant_function();
1061 ParameterCount expected(function); 1029 stub_compiler_->GenerateJumpFunction(object, function);
1062 __ InvokeFunction(function, expected, arguments_,
1063 JUMP_FUNCTION, NullCallWrapper(), call_kind);
1064 } 1030 }
1065 1031
1066 // Deferred code for fast API call case---clean preallocated space. 1032 // Deferred code for fast API call case---clean preallocated space.
1067 if (can_do_fast_api_call) { 1033 if (can_do_fast_api_call) {
1068 __ bind(&miss_cleanup); 1034 __ bind(&miss_cleanup);
1069 FreeSpaceForFastApiCall(masm); 1035 FreeSpaceForFastApiCall(masm);
1070 __ Branch(miss_label); 1036 __ Branch(miss_label);
1071 } 1037 }
1072 1038
1073 // Invoke a regular function. 1039 // Invoke a regular function.
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
1119 masm, receiver, holder, name_, holder_obj, 1085 masm, receiver, holder, name_, holder_obj,
1120 IC::kLoadPropertyWithInterceptorOnly); 1086 IC::kLoadPropertyWithInterceptorOnly);
1121 __ pop(name_); // Restore the name. 1087 __ pop(name_); // Restore the name.
1122 __ pop(receiver); // Restore the holder. 1088 __ pop(receiver); // Restore the holder.
1123 } 1089 }
1124 // If interceptor returns no-result sentinel, call the constant function. 1090 // If interceptor returns no-result sentinel, call the constant function.
1125 __ LoadRoot(scratch, Heap::kNoInterceptorResultSentinelRootIndex); 1091 __ LoadRoot(scratch, Heap::kNoInterceptorResultSentinelRootIndex);
1126 __ Branch(interceptor_succeeded, ne, v0, Operand(scratch)); 1092 __ Branch(interceptor_succeeded, ne, v0, Operand(scratch));
1127 } 1093 }
1128 1094
1129 StubCompiler* stub_compiler_; 1095 CallStubCompiler* stub_compiler_;
1130 const ParameterCount& arguments_; 1096 const ParameterCount& arguments_;
1131 Register name_; 1097 Register name_;
1132 ExtraICState extra_ic_state_; 1098 ExtraICState extra_ic_state_;
1133 }; 1099 };
1134 1100
1135 1101
1136 void StubCompiler::GenerateTailCall(MacroAssembler* masm, Handle<Code> code) { 1102 void StubCompiler::GenerateTailCall(MacroAssembler* masm, Handle<Code> code) {
1137 __ Jump(code, RelocInfo::CODE_TARGET); 1103 __ Jump(code, RelocInfo::CODE_TARGET);
1138 } 1104 }
1139 1105
(...skipping 380 matching lines...) Expand 10 before | Expand all | Expand 10 after
1520 } 1486 }
1521 1487
1522 1488
1523 void CallStubCompiler::GenerateNameCheck(Handle<Name> name, Label* miss) { 1489 void CallStubCompiler::GenerateNameCheck(Handle<Name> name, Label* miss) {
1524 if (kind_ == Code::KEYED_CALL_IC) { 1490 if (kind_ == Code::KEYED_CALL_IC) {
1525 __ Branch(miss, ne, a2, Operand(name)); 1491 __ Branch(miss, ne, a2, Operand(name));
1526 } 1492 }
1527 } 1493 }
1528 1494
1529 1495
1496 void CallStubCompiler::GenerateFunctionCheck(Register function,
1497 Register scratch,
1498 Label* miss) {
1499 __ JumpIfSmi(function, miss);
1500 __ GetObjectType(function, scratch, scratch);
1501 __ Branch(miss, ne, scratch, Operand(JS_FUNCTION_TYPE));
1502 }
1503
1504
1530 void CallStubCompiler::GenerateLoadFunctionFromCell( 1505 void CallStubCompiler::GenerateLoadFunctionFromCell(
1531 Handle<Cell> cell, 1506 Handle<Cell> cell,
1532 Handle<JSFunction> function, 1507 Handle<JSFunction> function,
1533 Label* miss) { 1508 Label* miss) {
1534 // Get the value from the cell. 1509 // Get the value from the cell.
1535 __ li(a3, Operand(cell)); 1510 __ li(a3, Operand(cell));
1536 __ lw(a1, FieldMemOperand(a3, Cell::kValueOffset)); 1511 __ lw(a1, FieldMemOperand(a3, Cell::kValueOffset));
1537 1512
1538 // Check that the cell contains the same function. 1513 // Check that the cell contains the same function.
1539 if (heap()->InNewSpace(*function)) { 1514 if (heap()->InNewSpace(*function)) {
1540 // We can't embed a pointer to a function in new space so we have 1515 // We can't embed a pointer to a function in new space so we have
1541 // to verify that the shared function info is unchanged. This has 1516 // to verify that the shared function info is unchanged. This has
1542 // the nice side effect that multiple closures based on the same 1517 // the nice side effect that multiple closures based on the same
1543 // function can all use this call IC. Before we load through the 1518 // function can all use this call IC. Before we load through the
1544 // function, we have to verify that it still is a function. 1519 // function, we have to verify that it still is a function.
1545 __ JumpIfSmi(a1, miss); 1520 GenerateFunctionCheck(a1, a3, miss);
1546 __ GetObjectType(a1, a3, a3);
1547 __ Branch(miss, ne, a3, Operand(JS_FUNCTION_TYPE));
1548 1521
1549 // Check the shared function info. Make sure it hasn't changed. 1522 // Check the shared function info. Make sure it hasn't changed.
1550 __ li(a3, Handle<SharedFunctionInfo>(function->shared())); 1523 __ li(a3, Handle<SharedFunctionInfo>(function->shared()));
1551 __ lw(t0, FieldMemOperand(a1, JSFunction::kSharedFunctionInfoOffset)); 1524 __ lw(t0, FieldMemOperand(a1, JSFunction::kSharedFunctionInfoOffset));
1552 __ Branch(miss, ne, t0, Operand(a3)); 1525 __ Branch(miss, ne, t0, Operand(a3));
1553 } else { 1526 } else {
1554 __ Branch(miss, ne, a1, Operand(function)); 1527 __ Branch(miss, ne, a1, Operand(function));
1555 } 1528 }
1556 } 1529 }
1557 1530
(...skipping 10 matching lines...) Expand all
1568 Handle<Code> CallStubCompiler::CompileCallField(Handle<JSObject> object, 1541 Handle<Code> CallStubCompiler::CompileCallField(Handle<JSObject> object,
1569 Handle<JSObject> holder, 1542 Handle<JSObject> holder,
1570 PropertyIndex index, 1543 PropertyIndex index,
1571 Handle<Name> name) { 1544 Handle<Name> name) {
1572 Label miss; 1545 Label miss;
1573 1546
1574 Register reg = HandlerFrontendHeader( 1547 Register reg = HandlerFrontendHeader(
1575 object, holder, name, RECEIVER_MAP_CHECK, &miss); 1548 object, holder, name, RECEIVER_MAP_CHECK, &miss);
1576 GenerateFastPropertyLoad(masm(), a1, reg, index.is_inobject(holder), 1549 GenerateFastPropertyLoad(masm(), a1, reg, index.is_inobject(holder),
1577 index.translate(holder), Representation::Tagged()); 1550 index.translate(holder), Representation::Tagged());
1578 1551 GenerateJumpFunction(object, a1, &miss);
1579 GenerateCallFunction(masm(), object, arguments(), &miss, extra_state_);
1580 1552
1581 HandlerFrontendFooter(&miss); 1553 HandlerFrontendFooter(&miss);
1582 1554
1583 // Return the generated code. 1555 // Return the generated code.
1584 return GetCode(Code::FAST, name); 1556 return GetCode(Code::FAST, name);
1585 } 1557 }
1586 1558
1587 1559
1588 Handle<Code> CallStubCompiler::CompileArrayCodeCall( 1560 Handle<Code> CallStubCompiler::CompileArrayCodeCall(
1589 Handle<Object> object, 1561 Handle<Object> object,
(...skipping 391 matching lines...) Expand 10 before | Expand all | Expand 10 after
1981 1953
1982 if (index_out_of_range.is_linked()) { 1954 if (index_out_of_range.is_linked()) {
1983 __ bind(&index_out_of_range); 1955 __ bind(&index_out_of_range);
1984 __ LoadRoot(v0, Heap::kNanValueRootIndex); 1956 __ LoadRoot(v0, Heap::kNanValueRootIndex);
1985 __ DropAndRet(argc + 1); 1957 __ DropAndRet(argc + 1);
1986 } 1958 }
1987 1959
1988 __ bind(&miss); 1960 __ bind(&miss);
1989 // Restore function name in a2. 1961 // Restore function name in a2.
1990 __ li(a2, name); 1962 __ li(a2, name);
1991 __ bind(&name_miss); 1963 HandlerFrontendFooter(&name_miss);
1992 GenerateMissBranch();
1993 1964
1994 // Return the generated code. 1965 // Return the generated code.
1995 return GetCode(type, name); 1966 return GetCode(type, name);
1996 } 1967 }
1997 1968
1998 1969
1999 Handle<Code> CallStubCompiler::CompileStringCharAtCall( 1970 Handle<Code> CallStubCompiler::CompileStringCharAtCall(
2000 Handle<Object> object, 1971 Handle<Object> object,
2001 Handle<JSObject> holder, 1972 Handle<JSObject> holder,
2002 Handle<Cell> cell, 1973 Handle<Cell> cell,
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
2046 2017
2047 if (index_out_of_range.is_linked()) { 2018 if (index_out_of_range.is_linked()) {
2048 __ bind(&index_out_of_range); 2019 __ bind(&index_out_of_range);
2049 __ LoadRoot(v0, Heap::kempty_stringRootIndex); 2020 __ LoadRoot(v0, Heap::kempty_stringRootIndex);
2050 __ DropAndRet(argc + 1); 2021 __ DropAndRet(argc + 1);
2051 } 2022 }
2052 2023
2053 __ bind(&miss); 2024 __ bind(&miss);
2054 // Restore function name in a2. 2025 // Restore function name in a2.
2055 __ li(a2, name); 2026 __ li(a2, name);
2056 __ bind(&name_miss); 2027 HandlerFrontendFooter(&name_miss);
2057 GenerateMissBranch();
2058 2028
2059 // Return the generated code. 2029 // Return the generated code.
2060 return GetCode(type, name); 2030 return GetCode(type, name);
2061 } 2031 }
2062 2032
2063 2033
2064 Handle<Code> CallStubCompiler::CompileStringFromCharCodeCall( 2034 Handle<Code> CallStubCompiler::CompileStringFromCharCodeCall(
2065 Handle<Object> object, 2035 Handle<Object> object,
2066 Handle<JSObject> holder, 2036 Handle<JSObject> holder,
2067 Handle<Cell> cell, 2037 Handle<Cell> cell,
(...skipping 25 matching lines...) Expand all
2093 // Convert the smi code to uint16. 2063 // Convert the smi code to uint16.
2094 __ And(code, code, Operand(Smi::FromInt(0xffff))); 2064 __ And(code, code, Operand(Smi::FromInt(0xffff)));
2095 2065
2096 StringCharFromCodeGenerator generator(code, v0); 2066 StringCharFromCodeGenerator generator(code, v0);
2097 generator.GenerateFast(masm()); 2067 generator.GenerateFast(masm());
2098 __ DropAndRet(argc + 1); 2068 __ DropAndRet(argc + 1);
2099 2069
2100 StubRuntimeCallHelper call_helper; 2070 StubRuntimeCallHelper call_helper;
2101 generator.GenerateSlow(masm(), call_helper); 2071 generator.GenerateSlow(masm(), call_helper);
2102 2072
2103 // Tail call the full function. We do not have to patch the receiver
2104 // because the function makes no use of it.
2105 __ bind(&slow); 2073 __ bind(&slow);
2106 ParameterCount expected(function); 2074 // We do not have to patch the receiver because the function makes no use of
2107 __ InvokeFunction(function, expected, arguments(), 2075 // it.
2108 JUMP_FUNCTION, NullCallWrapper(), CALL_AS_METHOD); 2076 GenerateJumpFunctionIgnoreReceiver(function);
2109 2077
2110 HandlerFrontendFooter(&miss); 2078 HandlerFrontendFooter(&miss);
2111 2079
2112 // Return the generated code. 2080 // Return the generated code.
2113 return GetCode(type, name); 2081 return GetCode(type, name);
2114 } 2082 }
2115 2083
2116 2084
2117 Handle<Code> CallStubCompiler::CompileMathFloorCall( 2085 Handle<Code> CallStubCompiler::CompileMathFloorCall(
2118 Handle<Object> object, 2086 Handle<Object> object,
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after
2204 // Restore FCSR and return. 2172 // Restore FCSR and return.
2205 __ ctc1(a3, FCSR); 2173 __ ctc1(a3, FCSR);
2206 2174
2207 __ DropAndRet(argc + 1); 2175 __ DropAndRet(argc + 1);
2208 2176
2209 __ bind(&wont_fit_smi); 2177 __ bind(&wont_fit_smi);
2210 // Restore FCSR and fall to slow case. 2178 // Restore FCSR and fall to slow case.
2211 __ ctc1(a3, FCSR); 2179 __ ctc1(a3, FCSR);
2212 2180
2213 __ bind(&slow); 2181 __ bind(&slow);
2214 // Tail call the full function. We do not have to patch the receiver 2182 // We do not have to patch the receiver because the function makes no use of
2215 // because the function makes no use of it. 2183 // it.
2216 ParameterCount expected(function); 2184 GenerateJumpFunctionIgnoreReceiver(function);
2217 __ InvokeFunction(function, expected, arguments(),
2218 JUMP_FUNCTION, NullCallWrapper(), CALL_AS_METHOD);
2219 2185
2220 HandlerFrontendFooter(&miss); 2186 HandlerFrontendFooter(&miss);
2221 2187
2222 // Return the generated code. 2188 // Return the generated code.
2223 return GetCode(type, name); 2189 return GetCode(type, name);
2224 } 2190 }
2225 2191
2226 2192
2227 Handle<Code> CallStubCompiler::CompileMathAbsCall( 2193 Handle<Code> CallStubCompiler::CompileMathAbsCall(
2228 Handle<Object> object, 2194 Handle<Object> object,
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
2285 // number. 2251 // number.
2286 __ bind(&negative_sign); 2252 __ bind(&negative_sign);
2287 __ Xor(a1, a1, Operand(HeapNumber::kSignMask)); 2253 __ Xor(a1, a1, Operand(HeapNumber::kSignMask));
2288 __ lw(a3, FieldMemOperand(v0, HeapNumber::kMantissaOffset)); 2254 __ lw(a3, FieldMemOperand(v0, HeapNumber::kMantissaOffset));
2289 __ LoadRoot(t2, Heap::kHeapNumberMapRootIndex); 2255 __ LoadRoot(t2, Heap::kHeapNumberMapRootIndex);
2290 __ AllocateHeapNumber(v0, t0, t1, t2, &slow); 2256 __ AllocateHeapNumber(v0, t0, t1, t2, &slow);
2291 __ sw(a1, FieldMemOperand(v0, HeapNumber::kExponentOffset)); 2257 __ sw(a1, FieldMemOperand(v0, HeapNumber::kExponentOffset));
2292 __ sw(a3, FieldMemOperand(v0, HeapNumber::kMantissaOffset)); 2258 __ sw(a3, FieldMemOperand(v0, HeapNumber::kMantissaOffset));
2293 __ DropAndRet(argc + 1); 2259 __ DropAndRet(argc + 1);
2294 2260
2295 // Tail call the full function. We do not have to patch the receiver
2296 // because the function makes no use of it.
2297 __ bind(&slow); 2261 __ bind(&slow);
2298 ParameterCount expected(function); 2262 // We do not have to patch the receiver because the function makes no use of
2299 __ InvokeFunction(function, expected, arguments(), 2263 // it.
2300 JUMP_FUNCTION, NullCallWrapper(), CALL_AS_METHOD); 2264 GenerateJumpFunctionIgnoreReceiver(function);
2301 2265
2302 HandlerFrontendFooter(&miss); 2266 HandlerFrontendFooter(&miss);
2303 2267
2304 // Return the generated code. 2268 // Return the generated code.
2305 return GetCode(type, name); 2269 return GetCode(type, name);
2306 } 2270 }
2307 2271
2308 2272
2309 Handle<Code> CallStubCompiler::CompileFastApiCall( 2273 Handle<Code> CallStubCompiler::CompileFastApiCall(
2310 const CallOptimization& optimization, 2274 const CallOptimization& optimization,
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
2345 // Check that the maps haven't changed and find a Holder as a side effect. 2309 // Check that the maps haven't changed and find a Holder as a side effect.
2346 CheckPrototypes( 2310 CheckPrototypes(
2347 IC::CurrentTypeOf(object, isolate()), 2311 IC::CurrentTypeOf(object, isolate()),
2348 a1, holder, a0, a3, t0, name, depth, &miss); 2312 a1, holder, a0, a3, t0, name, depth, &miss);
2349 2313
2350 GenerateFastApiDirectCall(masm(), optimization, argc, false); 2314 GenerateFastApiDirectCall(masm(), optimization, argc, false);
2351 2315
2352 __ bind(&miss); 2316 __ bind(&miss);
2353 FreeSpaceForFastApiCall(masm()); 2317 FreeSpaceForFastApiCall(masm());
2354 2318
2355 __ bind(&miss_before_stack_reserved); 2319 HandlerFrontendFooter(&miss_before_stack_reserved);
2356 GenerateMissBranch();
2357 2320
2358 // Return the generated code. 2321 // Return the generated code.
2359 return GetCode(function); 2322 return GetCode(function);
2360 } 2323 }
2361 2324
2362 2325
2363 void StubCompiler::GenerateBooleanCheck(Register object, Label* miss) { 2326 void StubCompiler::GenerateBooleanCheck(Register object, Label* miss) {
2364 Label success; 2327 Label success;
2365 // Check that the object is a boolean. 2328 // Check that the object is a boolean.
2366 __ LoadRoot(at, Heap::kTrueValueRootIndex); 2329 __ LoadRoot(at, Heap::kTrueValueRootIndex);
2367 __ Branch(&success, eq, object, Operand(at)); 2330 __ Branch(&success, eq, object, Operand(at));
2368 __ LoadRoot(at, Heap::kFalseValueRootIndex); 2331 __ LoadRoot(at, Heap::kFalseValueRootIndex);
2369 __ Branch(miss, ne, object, Operand(at)); 2332 __ Branch(miss, ne, object, Operand(at));
2370 __ bind(&success); 2333 __ bind(&success);
2371 } 2334 }
2372 2335
2373 2336
2374 void CallStubCompiler::PatchGlobalProxy(Handle<Object> object) { 2337 void CallStubCompiler::PatchGlobalProxy(Handle<Object> object) {
2375 if (object->IsGlobalObject()) { 2338 if (!object.is_null() && object->IsGlobalObject()) {
2376 const int argc = arguments().immediate(); 2339 const int argc = arguments().immediate();
2377 const int receiver_offset = argc * kPointerSize; 2340 const int receiver_offset = argc * kPointerSize;
2378 __ lw(a3, FieldMemOperand(a0, GlobalObject::kGlobalReceiverOffset)); 2341 __ lw(a3, FieldMemOperand(a0, GlobalObject::kGlobalReceiverOffset));
2379 __ sw(a3, MemOperand(sp, receiver_offset)); 2342 __ sw(a3, MemOperand(sp, receiver_offset));
2380 } 2343 }
2381 } 2344 }
2382 2345
2383 2346
2384 Register CallStubCompiler::HandlerFrontendHeader(Handle<Object> object, 2347 Register CallStubCompiler::HandlerFrontendHeader(Handle<Object> object,
2385 Handle<JSObject> holder, 2348 Handle<JSObject> holder,
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after
2461 Handle<Object> prototype(object->GetPrototype(isolate()), isolate()); 2424 Handle<Object> prototype(object->GetPrototype(isolate()), isolate());
2462 reg = CheckPrototypes( 2425 reg = CheckPrototypes(
2463 IC::CurrentTypeOf(prototype, isolate()), 2426 IC::CurrentTypeOf(prototype, isolate()),
2464 a1, holder, a1, a3, t0, name, miss); 2427 a1, holder, a1, a3, t0, name, miss);
2465 } 2428 }
2466 2429
2467 return reg; 2430 return reg;
2468 } 2431 }
2469 2432
2470 2433
2471 void CallStubCompiler::CompileHandlerBackend(Handle<JSFunction> function) { 2434 void CallStubCompiler::GenerateJumpFunction(Handle<Object> object,
2472 CallKind call_kind = CallICBase::Contextual::decode(extra_state_) 2435 Register function,
2473 ? CALL_AS_FUNCTION 2436 Label* miss) {
2474 : CALL_AS_METHOD; 2437 ASSERT(function.is(a1));
2475 ParameterCount expected(function); 2438 // Check that the function really is a function.
2476 __ InvokeFunction(function, expected, arguments(), 2439 GenerateFunctionCheck(function, a3, miss);
2477 JUMP_FUNCTION, NullCallWrapper(), call_kind); 2440 if (!function.is(a1)) __ mov(a1, function);
2441 PatchGlobalProxy(object);
2442 // Invoke the function.
2443 __ InvokeFunction(a1, arguments(), JUMP_FUNCTION,
2444 NullCallWrapper(), call_kind());
2478 } 2445 }
2479 2446
2480 2447
2481 Handle<Code> CallStubCompiler::CompileCallConstant(
2482 Handle<Object> object,
2483 Handle<JSObject> holder,
2484 Handle<Name> name,
2485 CheckType check,
2486 Handle<JSFunction> function) {
2487 if (HasCustomCallGenerator(function)) {
2488 Handle<Code> code = CompileCustomCall(object, holder,
2489 Handle<Cell>::null(),
2490 function, Handle<String>::cast(name),
2491 Code::FAST);
2492 // A null handle means bail out to the regular compiler code below.
2493 if (!code.is_null()) return code;
2494 }
2495
2496 Label miss;
2497 HandlerFrontendHeader(object, holder, name, check, &miss);
2498 PatchGlobalProxy(object);
2499 CompileHandlerBackend(function);
2500 HandlerFrontendFooter(&miss);
2501
2502 // Return the generated code.
2503 return GetCode(function);
2504 }
2505
2506
2507 Handle<Code> CallStubCompiler::CompileCallInterceptor(Handle<JSObject> object, 2448 Handle<Code> CallStubCompiler::CompileCallInterceptor(Handle<JSObject> object,
2508 Handle<JSObject> holder, 2449 Handle<JSObject> holder,
2509 Handle<Name> name) { 2450 Handle<Name> name) {
2510 Label miss; 2451 Label miss;
2511 2452
2512 GenerateNameCheck(name, &miss); 2453 GenerateNameCheck(name, &miss);
2513 2454
2514 // Get the number of arguments. 2455 // Get the number of arguments.
2515 const int argc = arguments().immediate(); 2456 const int argc = arguments().immediate();
2516 LookupResult lookup(isolate()); 2457 LookupResult lookup(isolate());
2517 LookupPostInterceptor(holder, name, &lookup); 2458 LookupPostInterceptor(holder, name, &lookup);
2518 2459
2519 // Get the receiver from the stack. 2460 // Get the receiver from the stack.
2520 __ lw(a1, MemOperand(sp, argc * kPointerSize)); 2461 __ lw(a1, MemOperand(sp, argc * kPointerSize));
2521 2462
2522 CallInterceptorCompiler compiler(this, arguments(), a2, extra_state_); 2463 CallInterceptorCompiler compiler(this, arguments(), a2, extra_state_);
2523 compiler.Compile(masm(), object, holder, name, &lookup, a1, a3, t0, a0, 2464 compiler.Compile(masm(), object, holder, name, &lookup, a1, a3, t0, a0,
2524 &miss); 2465 &miss);
2525 2466
2526 // Move returned value, the function to call, to a1. 2467 // Move returned value, the function to call, to a1.
2527 __ mov(a1, v0); 2468 __ mov(a1, v0);
2528 // Restore receiver. 2469 // Restore receiver.
2529 __ lw(a0, MemOperand(sp, argc * kPointerSize)); 2470 __ lw(a0, MemOperand(sp, argc * kPointerSize));
2530 2471
2531 GenerateCallFunction(masm(), object, arguments(), &miss, extra_state_); 2472 GenerateJumpFunction(object, a0, &miss);
2532 2473
2533 // Handle call cache miss. 2474 HandlerFrontendFooter(&miss);
2534 __ bind(&miss);
2535 GenerateMissBranch();
2536 2475
2537 // Return the generated code. 2476 // Return the generated code.
2538 return GetCode(Code::FAST, name); 2477 return GetCode(Code::FAST, name);
2539 } 2478 }
2540 2479
2541 2480
2542 Handle<Code> CallStubCompiler::CompileCallGlobal( 2481 Handle<Code> CallStubCompiler::CompileCallGlobal(
2543 Handle<JSObject> object, 2482 Handle<JSObject> object,
2544 Handle<GlobalObject> holder, 2483 Handle<GlobalObject> holder,
2545 Handle<PropertyCell> cell, 2484 Handle<PropertyCell> cell,
2546 Handle<JSFunction> function, 2485 Handle<JSFunction> function,
2547 Handle<Name> name) { 2486 Handle<Name> name) {
2548 if (HasCustomCallGenerator(function)) { 2487 if (HasCustomCallGenerator(function)) {
2549 Handle<Code> code = CompileCustomCall( 2488 Handle<Code> code = CompileCustomCall(
2550 object, holder, cell, function, Handle<String>::cast(name), 2489 object, holder, cell, function, Handle<String>::cast(name),
2551 Code::NORMAL); 2490 Code::NORMAL);
2552 // A null handle means bail out to the regular compiler code below. 2491 // A null handle means bail out to the regular compiler code below.
2553 if (!code.is_null()) return code; 2492 if (!code.is_null()) return code;
2554 } 2493 }
2555 2494
2556 Label miss; 2495 Label miss;
2557 HandlerFrontendHeader(object, holder, name, RECEIVER_MAP_CHECK, &miss); 2496 HandlerFrontendHeader(object, holder, name, RECEIVER_MAP_CHECK, &miss);
2497 // Potentially loads a closure that matches the shared function info of the
2498 // function, rather than function.
2558 GenerateLoadFunctionFromCell(cell, function, &miss); 2499 GenerateLoadFunctionFromCell(cell, function, &miss);
2559 PatchGlobalProxy(object);
2560
2561 // Set up the context (function already in r1).
2562 __ lw(cp, FieldMemOperand(a1, JSFunction::kContextOffset));
2563
2564 // Jump to the cached code (tail call).
2565 Counters* counters = isolate()->counters(); 2500 Counters* counters = isolate()->counters();
2566 __ IncrementCounter(counters->call_global_inline(), 1, a3, t0); 2501 __ IncrementCounter(counters->call_global_inline(), 1, a3, t0);
2567 ParameterCount expected(function->shared()->formal_parameter_count()); 2502 GenerateJumpFunction(object, a1, function);
2568 CallKind call_kind = CallICBase::Contextual::decode(extra_state_)
2569 ? CALL_AS_FUNCTION
2570 : CALL_AS_METHOD;
2571 // We call indirectly through the code field in the function to
2572 // allow recompilation to take effect without changing any of the
2573 // call sites.
2574 __ lw(a3, FieldMemOperand(a1, JSFunction::kCodeEntryOffset));
2575 __ InvokeCode(a3, expected, arguments(), JUMP_FUNCTION,
2576 NullCallWrapper(), call_kind);
2577
2578 HandlerFrontendFooter(&miss); 2503 HandlerFrontendFooter(&miss);
2579 2504
2580 // Return the generated code. 2505 // Return the generated code.
2581 return GetCode(Code::NORMAL, name); 2506 return GetCode(Code::NORMAL, name);
2582 } 2507 }
2583 2508
2584 2509
2585 Handle<Code> StoreStubCompiler::CompileStoreCallback( 2510 Handle<Code> StoreStubCompiler::CompileStoreCallback(
2586 Handle<JSObject> object, 2511 Handle<JSObject> object,
2587 Handle<JSObject> holder, 2512 Handle<JSObject> holder,
(...skipping 372 matching lines...) Expand 10 before | Expand all | Expand 10 after
2960 // ----------------------------------- 2885 // -----------------------------------
2961 TailCallBuiltin(masm, Builtins::kKeyedLoadIC_Miss); 2886 TailCallBuiltin(masm, Builtins::kKeyedLoadIC_Miss);
2962 } 2887 }
2963 2888
2964 2889
2965 #undef __ 2890 #undef __
2966 2891
2967 } } // namespace v8::internal 2892 } } // namespace v8::internal
2968 2893
2969 #endif // V8_TARGET_ARCH_MIPS 2894 #endif // V8_TARGET_ARCH_MIPS
OLDNEW
« no previous file with comments | « src/mips/macro-assembler-mips.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698