Index: src/ic/ic.cc |
diff --git a/src/ic/ic.cc b/src/ic/ic.cc |
index 0e751bd358167537daa697d4ae5904fb7b4cb26c..eea4629d048ca25da6f089495ef9c3643b4aa8d3 100644 |
--- a/src/ic/ic.cc |
+++ b/src/ic/ic.cc |
@@ -691,11 +691,8 @@ static bool AddOneReceiverMapIfMissing(MapHandleList* receiver_maps, |
return true; |
} |
-bool IC::UpdatePolymorphicIC(Handle<Name> name, Handle<Object> code) { |
- DCHECK(code->IsSmi() || code->IsCode()); |
- if (!code->IsSmi() && !Code::cast(*code)->is_handler()) { |
- return false; |
- } |
+bool IC::UpdatePolymorphicIC(Handle<Name> name, Handle<Object> handler) { |
+ DCHECK(IsHandler(*handler)); |
if (is_keyed() && state() != RECOMPUTE_HANDLER) return false; |
Handle<Map> map = receiver_map(); |
MapHandleList maps; |
@@ -735,16 +732,16 @@ bool IC::UpdatePolymorphicIC(Handle<Name> name, Handle<Object> code) { |
number_of_valid_maps++; |
if (number_of_valid_maps > 1 && is_keyed()) return false; |
if (number_of_valid_maps == 1) { |
- ConfigureVectorState(name, receiver_map(), code); |
+ ConfigureVectorState(name, receiver_map(), handler); |
} else { |
if (handler_to_overwrite >= 0) { |
- handlers.Set(handler_to_overwrite, code); |
+ handlers.Set(handler_to_overwrite, handler); |
if (!map.is_identical_to(maps.at(handler_to_overwrite))) { |
maps.Set(handler_to_overwrite, map); |
} |
} else { |
maps.Add(map); |
- handlers.Add(code); |
+ handlers.Add(handler); |
} |
ConfigureVectorState(name, &maps, &handlers); |
@@ -754,8 +751,7 @@ bool IC::UpdatePolymorphicIC(Handle<Name> name, Handle<Object> code) { |
} |
void IC::UpdateMonomorphicIC(Handle<Object> handler, Handle<Name> name) { |
- DCHECK(handler->IsSmi() || |
- (handler->IsCode() && Handle<Code>::cast(handler)->is_handler())); |
+ DCHECK(IsHandler(*handler)); |
ConfigureVectorState(name, receiver_map(), handler); |
} |
@@ -786,24 +782,26 @@ bool IC::IsTransitionOfMonomorphicTarget(Map* source_map, Map* target_map) { |
return transitioned_map == target_map; |
} |
-void IC::PatchCache(Handle<Name> name, Handle<Object> code) { |
- DCHECK(code->IsCode() || (code->IsSmi() && (kind() == Code::LOAD_IC || |
- kind() == Code::KEYED_LOAD_IC))); |
+void IC::PatchCache(Handle<Name> name, Handle<Object> handler) { |
+ DCHECK(IsHandler(*handler)); |
+ // Currently only LoadIC and KeyedLoadIC support non-code handlers. |
+ DCHECK_IMPLIES(!handler->IsCode(), |
+ kind() == Code::LOAD_IC || kind() == Code::KEYED_LOAD_IC); |
switch (state()) { |
case UNINITIALIZED: |
case PREMONOMORPHIC: |
- UpdateMonomorphicIC(code, name); |
+ UpdateMonomorphicIC(handler, name); |
break; |
case RECOMPUTE_HANDLER: |
case MONOMORPHIC: |
if (kind() == Code::LOAD_GLOBAL_IC) { |
- UpdateMonomorphicIC(code, name); |
+ UpdateMonomorphicIC(handler, name); |
break; |
} |
// Fall through. |
case POLYMORPHIC: |
if (!is_keyed() || state() == RECOMPUTE_HANDLER) { |
- if (UpdatePolymorphicIC(name, code)) break; |
+ if (UpdatePolymorphicIC(name, handler)) break; |
// For keyed stubs, we can't know whether old handlers were for the |
// same key. |
CopyICToMegamorphicCache(name); |
@@ -812,7 +810,7 @@ void IC::PatchCache(Handle<Name> name, Handle<Object> code) { |
ConfigureVectorState(MEGAMORPHIC, name); |
// Fall through. |
case MEGAMORPHIC: |
- UpdateMegamorphicCache(*receiver_map(), *name, *code); |
+ UpdateMegamorphicCache(*receiver_map(), *name, *handler); |
// Indicate that we've handled this case. |
DCHECK(UseVector()); |
vector_set_ = true; |
@@ -964,30 +962,17 @@ StubCache* IC::stub_cache() { |
return nullptr; |
} |
-void IC::UpdateMegamorphicCache(Map* map, Name* name, Object* code) { |
- if (code->IsSmi()) { |
- // TODO(jkummerow): Support Smis in the code cache. |
- Handle<Map> map_handle(map, isolate()); |
- Handle<Name> name_handle(name, isolate()); |
- FieldIndex index = |
- FieldIndex::ForLoadByFieldOffset(map, Smi::cast(code)->value()); |
- TRACE_HANDLER_STATS(isolate(), LoadIC_LoadFieldStub); |
- LoadFieldStub stub(isolate(), index); |
- Code* handler = *stub.GetCode(); |
- stub_cache()->Set(*name_handle, *map_handle, handler); |
- return; |
- } |
- DCHECK(code->IsCode()); |
- stub_cache()->Set(name, map, Code::cast(code)); |
+void IC::UpdateMegamorphicCache(Map* map, Name* name, Object* handler) { |
+ stub_cache()->Set(name, map, handler); |
} |
Handle<Object> IC::ComputeHandler(LookupIterator* lookup, |
Handle<Object> value) { |
// Try to find a globally shared handler stub. |
- Handle<Object> handler_or_index = GetMapIndependentHandler(lookup); |
- if (!handler_or_index.is_null()) { |
- DCHECK(handler_or_index->IsCode() || handler_or_index->IsSmi()); |
- return handler_or_index; |
+ Handle<Object> handler = GetMapIndependentHandler(lookup); |
+ if (!handler.is_null()) { |
+ DCHECK(IC::IsHandler(*handler)); |
+ return handler; |
} |
// Otherwise check the map's handler cache for a map-specific handler, and |
@@ -1024,8 +1009,9 @@ Handle<Object> IC::ComputeHandler(LookupIterator* lookup, |
// cache (which just missed) is different from the cached handler. |
if (state() == MEGAMORPHIC && lookup->GetReceiver()->IsHeapObject()) { |
Map* map = Handle<HeapObject>::cast(lookup->GetReceiver())->map(); |
- Code* megamorphic_cached_code = stub_cache()->Get(*lookup->name(), map); |
- if (megamorphic_cached_code != *code) { |
+ Object* megamorphic_cached_handler = |
+ stub_cache()->Get(*lookup->name(), map); |
+ if (megamorphic_cached_handler != *code) { |
TRACE_HANDLER_STATS(isolate(), IC_HandlerCacheHit); |
return code; |
} |