| Index: src/ic/ic.cc
|
| diff --git a/src/ic/ic.cc b/src/ic/ic.cc
|
| index 63f2ffa9d9d18b3344b2bd6f32c5acd748acbc35..6b47f035bfb18f43651153837498eafc6badc32f 100644
|
| --- a/src/ic/ic.cc
|
| +++ b/src/ic/ic.cc
|
| @@ -801,19 +801,27 @@ void IC::PatchCache(Handle<Name> name, Handle<Code> code) {
|
| case POLYMORPHIC:
|
| if (!target()->is_keyed_stub() || state() == PROTOTYPE_FAILURE) {
|
| if (UpdatePolymorphicIC(name, code)) break;
|
| + // For keyed stubs, we can't know whether old handlers were for the
|
| + // same key.
|
| CopyICToMegamorphicCache(name);
|
| }
|
| set_target(*megamorphic_stub());
|
| // Fall through.
|
| case MEGAMORPHIC:
|
| UpdateMegamorphicCache(*receiver_type(), *name, *code);
|
| + // Indicate that we've handled this case.
|
| + target_set_ = true;
|
| break;
|
| case DEBUG_STUB:
|
| break;
|
| case DEFAULT:
|
| - case GENERIC:
|
| UNREACHABLE();
|
| break;
|
| + case GENERIC:
|
| + // The generic keyed store stub re-uses store handlers, which can miss.
|
| + // That's ok, no reason to do anything.
|
| + DCHECK(target()->kind() == Code::KEYED_STORE_IC);
|
| + break;
|
| }
|
| }
|
|
|
| @@ -894,7 +902,8 @@ void LoadIC::UpdateCaches(LookupIterator* lookup) {
|
|
|
|
|
| void IC::UpdateMegamorphicCache(HeapType* type, Name* name, Code* code) {
|
| - if (kind() == Code::KEYED_LOAD_IC || kind() == Code::KEYED_STORE_IC) return;
|
| + // Megamorphic state isn't implemented for keyed loads currently.
|
| + if (kind() == Code::KEYED_LOAD_IC) return;
|
| Map* map = *TypeToMap(type, isolate());
|
| isolate()->stub_cache()->Set(name, map, code);
|
| }
|
| @@ -1365,9 +1374,9 @@ Handle<Code> StoreIC::megamorphic_stub() {
|
| } else {
|
| DCHECK(kind() == Code::KEYED_STORE_IC);
|
| if (strict_mode() == STRICT) {
|
| - return isolate()->builtins()->KeyedStoreIC_Generic_Strict();
|
| + return isolate()->builtins()->KeyedStoreIC_Megamorphic_Strict();
|
| } else {
|
| - return isolate()->builtins()->KeyedStoreIC_Generic();
|
| + return isolate()->builtins()->KeyedStoreIC_Megamorphic();
|
| }
|
| }
|
| }
|
| @@ -1813,12 +1822,12 @@ MaybeHandle<Object> KeyedStoreIC::Store(Handle<Object> object,
|
| StoreIC::Store(object, Handle<String>::cast(key), value,
|
| JSReceiver::MAY_BE_STORE_FROM_KEYED),
|
| Object);
|
| - // TODO(jkummerow): Ideally we'd wrap this in "if (!is_target_set())",
|
| - // but doing so causes Hydrogen crashes. Needs investigation.
|
| - TRACE_GENERIC_IC(isolate(), "KeyedStoreIC",
|
| - "unhandled internalized string key");
|
| - TRACE_IC("StoreIC", key);
|
| - set_target(*stub);
|
| + if (!is_target_set()) {
|
| + TRACE_GENERIC_IC(isolate(), "KeyedStoreIC",
|
| + "unhandled internalized string key");
|
| + TRACE_IC("StoreIC", key);
|
| + set_target(*stub);
|
| + }
|
| return store_handle;
|
| }
|
|
|
| @@ -2088,7 +2097,7 @@ RUNTIME_FUNCTION(StoreIC_Miss) {
|
| DCHECK(args.length() == 3);
|
| StoreIC ic(IC::NO_EXTRA_FRAME, isolate);
|
| Handle<Object> receiver = args.at<Object>(0);
|
| - Handle<String> key = args.at<String>(1);
|
| + Handle<Name> key = args.at<Name>(1);
|
| ic.UpdateState(receiver, key);
|
| Handle<Object> result;
|
| ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
|
| @@ -2103,7 +2112,7 @@ RUNTIME_FUNCTION(StoreIC_MissFromStubFailure) {
|
| DCHECK(args.length() == 3 || args.length() == 4);
|
| StoreIC ic(IC::EXTRA_CALL_FRAME, isolate);
|
| Handle<Object> receiver = args.at<Object>(0);
|
| - Handle<String> key = args.at<String>(1);
|
| + Handle<Name> key = args.at<Name>(1);
|
| ic.UpdateState(receiver, key);
|
| Handle<Object> result;
|
| ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
|
|
|