OLD | NEW |
1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 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 775 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
786 return CallICBase::LoadFunction(state, | 786 return CallICBase::LoadFunction(state, |
787 Code::kNoExtraICState, | 787 Code::kNoExtraICState, |
788 object, | 788 object, |
789 Handle<String>::cast(key)); | 789 Handle<String>::cast(key)); |
790 } | 790 } |
791 | 791 |
792 if (object->IsUndefined() || object->IsNull()) { | 792 if (object->IsUndefined() || object->IsNull()) { |
793 return TypeError("non_object_property_call", object, key); | 793 return TypeError("non_object_property_call", object, key); |
794 } | 794 } |
795 | 795 |
796 if (FLAG_use_ic && state != MEGAMORPHIC && object->IsHeapObject()) { | 796 if (FLAG_use_ic && state != MEGAMORPHIC && !object->IsAccessCheckNeeded()) { |
797 int argc = target()->arguments_count(); | 797 int argc = target()->arguments_count(); |
798 InLoopFlag in_loop = target()->ic_in_loop(); | 798 InLoopFlag in_loop = target()->ic_in_loop(); |
799 Heap* heap = Handle<HeapObject>::cast(object)->GetHeap(); | 799 MaybeObject* maybe_code = isolate()->stub_cache()->ComputeCallMegamorphic( |
800 Map* map = heap->non_strict_arguments_elements_map(); | 800 argc, in_loop, Code::KEYED_CALL_IC, Code::kNoExtraICState); |
801 if (object->IsJSObject() && | 801 Object* code; |
802 Handle<JSObject>::cast(object)->elements()->map() == map) { | 802 if (maybe_code->ToObject(&code)) { |
803 MaybeObject* maybe_code = isolate()->stub_cache()->ComputeCallArguments( | 803 set_target(Code::cast(code)); |
804 argc, in_loop, Code::KEYED_CALL_IC); | |
805 Object* code; | |
806 if (maybe_code->ToObject(&code)) { | |
807 set_target(Code::cast(code)); | |
808 #ifdef DEBUG | 804 #ifdef DEBUG |
809 TraceIC( | 805 TraceIC( |
810 "KeyedCallIC", key, state, target(), in_loop ? " (in-loop)" : ""); | 806 "KeyedCallIC", key, state, target(), in_loop ? " (in-loop)" : ""); |
811 #endif | 807 #endif |
812 } | |
813 } else if (FLAG_use_ic && state != MEGAMORPHIC && | |
814 !object->IsAccessCheckNeeded()) { | |
815 MaybeObject* maybe_code = isolate()->stub_cache()->ComputeCallMegamorphic( | |
816 argc, in_loop, Code::KEYED_CALL_IC, Code::kNoExtraICState); | |
817 Object* code; | |
818 if (maybe_code->ToObject(&code)) { | |
819 set_target(Code::cast(code)); | |
820 #ifdef DEBUG | |
821 TraceIC( | |
822 "KeyedCallIC", key, state, target(), in_loop ? " (in-loop)" : ""); | |
823 #endif | |
824 } | |
825 } | 808 } |
826 } | 809 } |
827 | 810 |
828 HandleScope scope(isolate()); | 811 HandleScope scope(isolate()); |
829 Handle<Object> result = GetProperty(object, key); | 812 Handle<Object> result = GetProperty(object, key); |
830 RETURN_IF_EMPTY_HANDLE(isolate(), result); | 813 RETURN_IF_EMPTY_HANDLE(isolate(), result); |
831 | 814 |
832 // Make receiver an object if the callee requires it. Strict mode or builtin | 815 // Make receiver an object if the callee requires it. Strict mode or builtin |
833 // functions do not wrap the receiver, non-strict functions and objects | 816 // functions do not wrap the receiver, non-strict functions and objects |
834 // called as functions do. | 817 // called as functions do. |
(...skipping 412 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1247 | 1230 |
1248 if (use_ic) { | 1231 if (use_ic) { |
1249 Code* stub = generic_stub(); | 1232 Code* stub = generic_stub(); |
1250 if (!force_generic_stub) { | 1233 if (!force_generic_stub) { |
1251 if (object->IsString() && key->IsNumber()) { | 1234 if (object->IsString() && key->IsNumber()) { |
1252 if (state == UNINITIALIZED) { | 1235 if (state == UNINITIALIZED) { |
1253 stub = string_stub(); | 1236 stub = string_stub(); |
1254 } | 1237 } |
1255 } else if (object->IsJSObject()) { | 1238 } else if (object->IsJSObject()) { |
1256 JSObject* receiver = JSObject::cast(*object); | 1239 JSObject* receiver = JSObject::cast(*object); |
1257 Heap* heap = Handle<JSObject>::cast(object)->GetHeap(); | 1240 if (receiver->HasIndexedInterceptor()) { |
1258 Map* elements_map = Handle<JSObject>::cast(object)->elements()->map(); | |
1259 if (elements_map == heap->non_strict_arguments_elements_map()) { | |
1260 stub = non_strict_arguments_stub(); | |
1261 } else if (receiver->HasIndexedInterceptor()) { | |
1262 stub = indexed_interceptor_stub(); | 1241 stub = indexed_interceptor_stub(); |
1263 } else if (key->IsSmi() && (target() != non_strict_arguments_stub())) { | 1242 } else if (key->IsSmi()) { |
1264 MaybeObject* maybe_stub = ComputeStub(receiver, | 1243 MaybeObject* maybe_stub = ComputeStub(receiver, |
1265 false, | 1244 false, |
1266 kNonStrictMode, | 1245 kNonStrictMode, |
1267 stub); | 1246 stub); |
1268 stub = maybe_stub->IsFailure() ? | 1247 stub = maybe_stub->IsFailure() ? |
1269 NULL : Code::cast(maybe_stub->ToObjectUnchecked()); | 1248 NULL : Code::cast(maybe_stub->ToObjectUnchecked()); |
1270 } | 1249 } |
1271 } | 1250 } |
1272 } | 1251 } |
1273 if (stub != NULL) set_target(stub); | 1252 if (stub != NULL) set_target(stub); |
(...skipping 549 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1823 | 1802 |
1824 // Do not use ICs for objects that require access checks (including | 1803 // Do not use ICs for objects that require access checks (including |
1825 // the global object). | 1804 // the global object). |
1826 bool use_ic = FLAG_use_ic && !object->IsAccessCheckNeeded(); | 1805 bool use_ic = FLAG_use_ic && !object->IsAccessCheckNeeded(); |
1827 ASSERT(!(use_ic && object->IsJSGlobalProxy())); | 1806 ASSERT(!(use_ic && object->IsJSGlobalProxy())); |
1828 | 1807 |
1829 if (use_ic) { | 1808 if (use_ic) { |
1830 Code* stub = (strict_mode == kStrictMode) | 1809 Code* stub = (strict_mode == kStrictMode) |
1831 ? generic_stub_strict() | 1810 ? generic_stub_strict() |
1832 : generic_stub(); | 1811 : generic_stub(); |
1833 if (object->IsJSObject()) { | 1812 if (!force_generic) { |
1834 JSObject* receiver = JSObject::cast(*object); | 1813 if (object->IsJSObject() && key->IsSmi()) { |
1835 Heap* heap = Handle<JSObject>::cast(object)->GetHeap(); | 1814 JSObject* receiver = JSObject::cast(*object); |
1836 Map* elements_map = Handle<JSObject>::cast(object)->elements()->map(); | 1815 MaybeObject* maybe_stub = ComputeStub(receiver, |
1837 if (elements_map == heap->non_strict_arguments_elements_map()) { | 1816 true, |
1838 stub = non_strict_arguments_stub(); | 1817 strict_mode, |
1839 } else if (!force_generic) { | 1818 stub); |
1840 if (key->IsSmi() && (target() != non_strict_arguments_stub())) { | 1819 stub = maybe_stub->IsFailure() ? |
1841 MaybeObject* maybe_stub = ComputeStub(receiver, | 1820 NULL : Code::cast(maybe_stub->ToObjectUnchecked()); |
1842 true, | |
1843 strict_mode, | |
1844 stub); | |
1845 stub = maybe_stub->IsFailure() ? | |
1846 NULL : Code::cast(maybe_stub->ToObjectUnchecked()); | |
1847 } | |
1848 } | 1821 } |
1849 } | 1822 } |
1850 if (stub != NULL) set_target(stub); | 1823 if (stub != NULL) set_target(stub); |
1851 } | 1824 } |
1852 | 1825 |
1853 #ifdef DEBUG | 1826 #ifdef DEBUG |
1854 TraceIC("KeyedStoreIC", key, state, target()); | 1827 TraceIC("KeyedStoreIC", key, state, target()); |
1855 #endif | 1828 #endif |
1856 | 1829 |
1857 // Set the property. | 1830 // Set the property. |
(...skipping 685 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2543 #undef ADDR | 2516 #undef ADDR |
2544 }; | 2517 }; |
2545 | 2518 |
2546 | 2519 |
2547 Address IC::AddressFromUtilityId(IC::UtilityId id) { | 2520 Address IC::AddressFromUtilityId(IC::UtilityId id) { |
2548 return IC_utilities[id]; | 2521 return IC_utilities[id]; |
2549 } | 2522 } |
2550 | 2523 |
2551 | 2524 |
2552 } } // namespace v8::internal | 2525 } } // namespace v8::internal |
OLD | NEW |