OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "src/ic/ic.h" | 5 #include "src/ic/ic.h" |
6 | 6 |
7 #include <iostream> | 7 #include <iostream> |
8 | 8 |
9 #include "src/accessors.h" | 9 #include "src/accessors.h" |
10 #include "src/api-arguments-inl.h" | 10 #include "src/api-arguments-inl.h" |
(...skipping 2584 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2595 return *function; | 2595 return *function; |
2596 } | 2596 } |
2597 | 2597 |
2598 | 2598 |
2599 // Used from ic-<arch>.cc. | 2599 // Used from ic-<arch>.cc. |
2600 RUNTIME_FUNCTION(Runtime_LoadIC_Miss) { | 2600 RUNTIME_FUNCTION(Runtime_LoadIC_Miss) { |
2601 HandleScope scope(isolate); | 2601 HandleScope scope(isolate); |
2602 DCHECK_EQ(4, args.length()); | 2602 DCHECK_EQ(4, args.length()); |
2603 // Runtime functions don't follow the IC's calling convention. | 2603 // Runtime functions don't follow the IC's calling convention. |
2604 Handle<Object> receiver = args.at<Object>(0); | 2604 Handle<Object> receiver = args.at<Object>(0); |
| 2605 Handle<Name> key = args.at<Name>(1); |
2605 Handle<Smi> slot = args.at<Smi>(2); | 2606 Handle<Smi> slot = args.at<Smi>(2); |
2606 Handle<TypeFeedbackVector> vector = args.at<TypeFeedbackVector>(3); | 2607 Handle<TypeFeedbackVector> vector = args.at<TypeFeedbackVector>(3); |
2607 FeedbackVectorSlot vector_slot = vector->ToSlot(slot->value()); | 2608 FeedbackVectorSlot vector_slot = vector->ToSlot(slot->value()); |
2608 // A monomorphic or polymorphic KeyedLoadIC with a string key can call the | 2609 // A monomorphic or polymorphic KeyedLoadIC with a string key can call the |
2609 // LoadIC miss handler if the handler misses. Since the vector Nexus is | 2610 // LoadIC miss handler if the handler misses. Since the vector Nexus is |
2610 // set up outside the IC, handle that here. | 2611 // set up outside the IC, handle that here. |
2611 FeedbackVectorSlotKind kind = vector->GetKind(vector_slot); | 2612 FeedbackVectorSlotKind kind = vector->GetKind(vector_slot); |
2612 if (kind == FeedbackVectorSlotKind::LOAD_IC) { | 2613 if (kind == FeedbackVectorSlotKind::LOAD_IC) { |
2613 Handle<Name> key = args.at<Name>(1); | |
2614 LoadICNexus nexus(vector, vector_slot); | 2614 LoadICNexus nexus(vector, vector_slot); |
2615 LoadIC ic(IC::NO_EXTRA_FRAME, isolate, &nexus); | 2615 LoadIC ic(IC::NO_EXTRA_FRAME, isolate, &nexus); |
2616 ic.UpdateState(receiver, key); | 2616 ic.UpdateState(receiver, key); |
2617 RETURN_RESULT_OR_FAILURE(isolate, ic.Load(receiver, key)); | 2617 RETURN_RESULT_OR_FAILURE(isolate, ic.Load(receiver, key)); |
2618 | 2618 |
2619 } else if (kind == FeedbackVectorSlotKind::LOAD_GLOBAL_IC) { | 2619 } else if (kind == FeedbackVectorSlotKind::LOAD_GLOBAL_IC) { |
2620 Handle<Name> key(vector->GetName(vector_slot), isolate); | |
2621 DCHECK_NE(*key, isolate->heap()->empty_string()); | |
2622 DCHECK_EQ(*isolate->global_object(), *receiver); | 2620 DCHECK_EQ(*isolate->global_object(), *receiver); |
2623 LoadGlobalICNexus nexus(vector, vector_slot); | 2621 LoadGlobalICNexus nexus(vector, vector_slot); |
2624 LoadGlobalIC ic(IC::NO_EXTRA_FRAME, isolate, &nexus); | 2622 LoadGlobalIC ic(IC::NO_EXTRA_FRAME, isolate, &nexus); |
2625 ic.UpdateState(receiver, key); | 2623 ic.UpdateState(receiver, key); |
2626 RETURN_RESULT_OR_FAILURE(isolate, ic.Load(key)); | 2624 RETURN_RESULT_OR_FAILURE(isolate, ic.Load(key)); |
2627 | 2625 |
2628 } else { | 2626 } else { |
2629 Handle<Name> key = args.at<Name>(1); | |
2630 DCHECK_EQ(FeedbackVectorSlotKind::KEYED_LOAD_IC, kind); | 2627 DCHECK_EQ(FeedbackVectorSlotKind::KEYED_LOAD_IC, kind); |
2631 KeyedLoadICNexus nexus(vector, vector_slot); | 2628 KeyedLoadICNexus nexus(vector, vector_slot); |
2632 KeyedLoadIC ic(IC::NO_EXTRA_FRAME, isolate, &nexus); | 2629 KeyedLoadIC ic(IC::NO_EXTRA_FRAME, isolate, &nexus); |
2633 ic.UpdateState(receiver, key); | 2630 ic.UpdateState(receiver, key); |
2634 RETURN_RESULT_OR_FAILURE(isolate, ic.Load(receiver, key)); | 2631 RETURN_RESULT_OR_FAILURE(isolate, ic.Load(receiver, key)); |
2635 } | 2632 } |
2636 } | 2633 } |
2637 | 2634 |
2638 // Used from ic-<arch>.cc. | 2635 // Used from ic-<arch>.cc. |
2639 RUNTIME_FUNCTION(Runtime_LoadGlobalIC_Miss) { | 2636 RUNTIME_FUNCTION(Runtime_LoadGlobalIC_Miss) { |
2640 HandleScope scope(isolate); | 2637 HandleScope scope(isolate); |
2641 DCHECK_EQ(2, args.length()); | 2638 DCHECK_EQ(3, args.length()); |
2642 // Runtime functions don't follow the IC's calling convention. | 2639 // Runtime functions don't follow the IC's calling convention. |
2643 Handle<JSGlobalObject> global = isolate->global_object(); | 2640 Handle<JSGlobalObject> global = isolate->global_object(); |
2644 Handle<Smi> slot = args.at<Smi>(0); | 2641 Handle<String> name = args.at<String>(0); |
2645 Handle<TypeFeedbackVector> vector = args.at<TypeFeedbackVector>(1); | 2642 Handle<Smi> slot = args.at<Smi>(1); |
| 2643 Handle<TypeFeedbackVector> vector = args.at<TypeFeedbackVector>(2); |
2646 FeedbackVectorSlot vector_slot = vector->ToSlot(slot->value()); | 2644 FeedbackVectorSlot vector_slot = vector->ToSlot(slot->value()); |
2647 DCHECK_EQ(FeedbackVectorSlotKind::LOAD_GLOBAL_IC, | |
2648 vector->GetKind(vector_slot)); | |
2649 Handle<String> name(vector->GetName(vector_slot), isolate); | |
2650 DCHECK_NE(*name, isolate->heap()->empty_string()); | |
2651 | 2645 |
2652 LoadGlobalICNexus nexus(vector, vector_slot); | 2646 LoadGlobalICNexus nexus(vector, vector_slot); |
2653 LoadGlobalIC ic(IC::NO_EXTRA_FRAME, isolate, &nexus); | 2647 LoadGlobalIC ic(IC::NO_EXTRA_FRAME, isolate, &nexus); |
2654 ic.UpdateState(global, name); | 2648 ic.UpdateState(global, name); |
2655 | 2649 |
2656 Handle<Object> result; | 2650 Handle<Object> result; |
2657 ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, result, ic.Load(name)); | 2651 ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, result, ic.Load(name)); |
2658 return *result; | 2652 return *result; |
2659 } | 2653 } |
2660 | 2654 |
2661 RUNTIME_FUNCTION(Runtime_LoadGlobalIC_Slow) { | 2655 RUNTIME_FUNCTION(Runtime_LoadGlobalIC_Slow) { |
2662 HandleScope scope(isolate); | 2656 HandleScope scope(isolate); |
2663 DCHECK_EQ(2, args.length()); | 2657 DCHECK_EQ(1, args.length()); |
2664 CONVERT_SMI_ARG_CHECKED(slot, 0); | 2658 CONVERT_ARG_HANDLE_CHECKED(String, name, 0); |
2665 CONVERT_ARG_HANDLE_CHECKED(TypeFeedbackVector, vector, 1); | |
2666 | 2659 |
2667 FeedbackVectorSlot vector_slot = vector->ToSlot(slot); | 2660 Handle<Context> native_context = isolate->native_context(); |
2668 DCHECK_EQ(FeedbackVectorSlotKind::LOAD_GLOBAL_IC, | |
2669 vector->GetKind(vector_slot)); | |
2670 Handle<String> name(vector->GetName(vector_slot), isolate); | |
2671 DCHECK_NE(*name, isolate->heap()->empty_string()); | |
2672 | |
2673 Handle<JSGlobalObject> global = isolate->global_object(); | |
2674 | |
2675 Handle<ScriptContextTable> script_contexts( | 2661 Handle<ScriptContextTable> script_contexts( |
2676 global->native_context()->script_context_table()); | 2662 native_context->script_context_table()); |
2677 | 2663 |
2678 ScriptContextTable::LookupResult lookup_result; | 2664 ScriptContextTable::LookupResult lookup_result; |
2679 if (ScriptContextTable::Lookup(script_contexts, name, &lookup_result)) { | 2665 if (ScriptContextTable::Lookup(script_contexts, name, &lookup_result)) { |
2680 Handle<Context> script_context = ScriptContextTable::GetContext( | 2666 Handle<Context> script_context = ScriptContextTable::GetContext( |
2681 script_contexts, lookup_result.context_index); | 2667 script_contexts, lookup_result.context_index); |
2682 Handle<Object> result = | 2668 Handle<Object> result = |
2683 FixedArray::get(*script_context, lookup_result.slot_index, isolate); | 2669 FixedArray::get(*script_context, lookup_result.slot_index, isolate); |
2684 if (*result == isolate->heap()->the_hole_value()) { | 2670 if (*result == isolate->heap()->the_hole_value()) { |
2685 THROW_NEW_ERROR_RETURN_FAILURE( | 2671 THROW_NEW_ERROR_RETURN_FAILURE( |
2686 isolate, NewReferenceError(MessageTemplate::kNotDefined, name)); | 2672 isolate, NewReferenceError(MessageTemplate::kNotDefined, name)); |
2687 } | 2673 } |
2688 return *result; | 2674 return *result; |
2689 } | 2675 } |
2690 | 2676 |
| 2677 Handle<JSGlobalObject> global(native_context->global_object(), isolate); |
2691 Handle<Object> result; | 2678 Handle<Object> result; |
2692 bool is_found = false; | 2679 bool is_found = false; |
2693 ASSIGN_RETURN_FAILURE_ON_EXCEPTION( | 2680 ASSIGN_RETURN_FAILURE_ON_EXCEPTION( |
2694 isolate, result, | 2681 isolate, result, |
2695 Runtime::GetObjectProperty(isolate, global, name, &is_found)); | 2682 Runtime::GetObjectProperty(isolate, global, name, &is_found)); |
2696 if (!is_found) { | 2683 if (!is_found) { |
2697 LoadICNexus nexus(isolate); | 2684 LoadICNexus nexus(isolate); |
2698 LoadIC ic(IC::NO_EXTRA_FRAME, isolate, &nexus); | 2685 LoadIC ic(IC::NO_EXTRA_FRAME, isolate, &nexus); |
2699 // It is actually a LoadGlobalICs here but the predicate handles this case | 2686 // It is actually a LoadGlobalICs here but the predicate handles this case |
2700 // properly. | 2687 // properly. |
(...skipping 543 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3244 DCHECK_EQ(LookupIterator::INTERCEPTOR, it.state()); | 3231 DCHECK_EQ(LookupIterator::INTERCEPTOR, it.state()); |
3245 it.Next(); | 3232 it.Next(); |
3246 ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, result, | 3233 ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, result, |
3247 Object::GetProperty(&it)); | 3234 Object::GetProperty(&it)); |
3248 } | 3235 } |
3249 | 3236 |
3250 return *result; | 3237 return *result; |
3251 } | 3238 } |
3252 } // namespace internal | 3239 } // namespace internal |
3253 } // namespace v8 | 3240 } // namespace v8 |
OLD | NEW |