| Index: src/ic.cc
|
| diff --git a/src/ic.cc b/src/ic.cc
|
| index 02f2f0f33ba0bfd32bafe0fcbf33a4fa86b6e314..dc15194ec94432419b73f1d8c74bcad458e5c305 100644
|
| --- a/src/ic.cc
|
| +++ b/src/ic.cc
|
| @@ -217,9 +217,11 @@ static bool TryRemoveInvalidPrototypeDependentStub(Code* target,
|
| int index = map->IndexInCodeCache(name, target);
|
| if (index >= 0) {
|
| map->RemoveFromCodeCache(String::cast(name), target, index);
|
| - // For loads, handlers are stored in addition to the ICs on the map. Remove
|
| - // those, too.
|
| - if (target->is_load_stub() || target->is_keyed_load_stub()) {
|
| + // For loads and stores, handlers are stored in addition to the ICs on the
|
| + // map. Remove those, too.
|
| + if ((target->is_load_stub() || target->is_keyed_load_stub() ||
|
| + target->is_store_stub() || target->is_keyed_store_stub()) &&
|
| + target->type() != Code::NORMAL) {
|
| Code* handler = target->FindFirstCode();
|
| index = map->IndexInCodeCache(name, handler);
|
| if (index >= 0) {
|
| @@ -972,10 +974,10 @@ static bool AddOneReceiverMapIfMissing(MapHandleList* receiver_maps,
|
|
|
|
|
| bool IC::UpdatePolymorphicIC(State state,
|
| - StrictModeFlag strict_mode,
|
| Handle<JSObject> receiver,
|
| Handle<String> name,
|
| - Handle<Code> code) {
|
| + Handle<Code> code,
|
| + StrictModeFlag strict_mode) {
|
| if (code->type() == Code::NORMAL) return false;
|
| if (target()->ic_state() == MONOMORPHIC &&
|
| target()->type() == Code::NORMAL) {
|
| @@ -1026,18 +1028,39 @@ bool IC::UpdatePolymorphicIC(State state,
|
| handlers.Add(code);
|
| }
|
|
|
| - Handle<Code> ic = isolate()->stub_cache()->ComputePolymorphicIC(
|
| - &receiver_maps, &handlers, number_of_valid_maps, name);
|
| + Handle<Code> ic = ComputePolymorphicIC(
|
| + &receiver_maps, &handlers, number_of_valid_maps, name, strict_mode);
|
| set_target(*ic);
|
| return true;
|
| }
|
|
|
|
|
| +Handle<Code> LoadIC::ComputePolymorphicIC(MapHandleList* receiver_maps,
|
| + CodeHandleList* handlers,
|
| + int number_of_valid_maps,
|
| + Handle<Name> name,
|
| + StrictModeFlag strict_mode) {
|
| + return isolate()->stub_cache()->ComputePolymorphicLoadIC(
|
| + receiver_maps, handlers, number_of_valid_maps, name);
|
| +}
|
| +
|
| +
|
| +Handle<Code> StoreIC::ComputePolymorphicIC(MapHandleList* receiver_maps,
|
| + CodeHandleList* handlers,
|
| + int number_of_valid_maps,
|
| + Handle<Name> name,
|
| + StrictModeFlag strict_mode) {
|
| + return isolate()->stub_cache()->ComputePolymorphicStoreIC(
|
| + receiver_maps, handlers, number_of_valid_maps, name, strict_mode);
|
| +}
|
| +
|
| +
|
| void LoadIC::UpdateMonomorphicIC(Handle<JSObject> receiver,
|
| Handle<Code> handler,
|
| - Handle<String> name) {
|
| + Handle<String> name,
|
| + StrictModeFlag strict_mode) {
|
| if (handler->type() == Code::NORMAL) return set_target(*handler);
|
| - Handle<Code> ic = isolate()->stub_cache()->ComputeMonomorphicIC(
|
| + Handle<Code> ic = isolate()->stub_cache()->ComputeMonomorphicLoadIC(
|
| receiver, handler, name);
|
| set_target(*ic);
|
| }
|
| @@ -1045,14 +1068,37 @@ void LoadIC::UpdateMonomorphicIC(Handle<JSObject> receiver,
|
|
|
| void KeyedLoadIC::UpdateMonomorphicIC(Handle<JSObject> receiver,
|
| Handle<Code> handler,
|
| - Handle<String> name) {
|
| + Handle<String> name,
|
| + StrictModeFlag strict_mode) {
|
| if (handler->type() == Code::NORMAL) return set_target(*handler);
|
| - Handle<Code> ic = isolate()->stub_cache()->ComputeKeyedMonomorphicIC(
|
| + Handle<Code> ic = isolate()->stub_cache()->ComputeMonomorphicKeyedLoadIC(
|
| receiver, handler, name);
|
| set_target(*ic);
|
| }
|
|
|
|
|
| +void StoreIC::UpdateMonomorphicIC(Handle<JSObject> receiver,
|
| + Handle<Code> handler,
|
| + Handle<String> name,
|
| + StrictModeFlag strict_mode) {
|
| + if (handler->type() == Code::NORMAL) return set_target(*handler);
|
| + Handle<Code> ic = isolate()->stub_cache()->ComputeMonomorphicStoreIC(
|
| + receiver, handler, name, strict_mode);
|
| + set_target(*ic);
|
| +}
|
| +
|
| +
|
| +void KeyedStoreIC::UpdateMonomorphicIC(Handle<JSObject> receiver,
|
| + Handle<Code> handler,
|
| + Handle<String> name,
|
| + StrictModeFlag strict_mode) {
|
| + if (handler->type() == Code::NORMAL) return set_target(*handler);
|
| + Handle<Code> ic = isolate()->stub_cache()->ComputeMonomorphicKeyedStoreIC(
|
| + receiver, handler, name, strict_mode);
|
| + set_target(*ic);
|
| +}
|
| +
|
| +
|
| void IC::CopyICToMegamorphicCache(Handle<String> name) {
|
| MapHandleList receiver_maps;
|
| CodeHandleList handlers;
|
| @@ -1094,12 +1140,12 @@ void IC::PatchCache(State state,
|
| case UNINITIALIZED:
|
| case PREMONOMORPHIC:
|
| case MONOMORPHIC_PROTOTYPE_FAILURE:
|
| - UpdateMonomorphicIC(receiver, code, name);
|
| + UpdateMonomorphicIC(receiver, code, name, strict_mode);
|
| break;
|
| case MONOMORPHIC:
|
| // Only move to megamorphic if the target changes.
|
| if (target() != *code) {
|
| - if (target()->is_load_stub()) {
|
| + if (target()->is_load_stub() || target()->is_store_stub()) {
|
| bool is_same_handler = false;
|
| {
|
| DisallowHeapAllocation no_allocation;
|
| @@ -1108,10 +1154,10 @@ void IC::PatchCache(State state,
|
| }
|
| if (is_same_handler
|
| && IsTransitionedMapOfMonomorphicTarget(receiver->map())) {
|
| - UpdateMonomorphicIC(receiver, code, name);
|
| + UpdateMonomorphicIC(receiver, code, name, strict_mode);
|
| break;
|
| }
|
| - if (UpdatePolymorphicIC(state, strict_mode, receiver, name, code)) {
|
| + if (UpdatePolymorphicIC(state, receiver, name, code, strict_mode)) {
|
| break;
|
| }
|
|
|
| @@ -1131,13 +1177,15 @@ void IC::PatchCache(State state,
|
| UpdateMegamorphicCache(receiver->map(), *name, *code);
|
| break;
|
| case POLYMORPHIC:
|
| - if (target()->is_load_stub()) {
|
| - if (UpdatePolymorphicIC(state, strict_mode, receiver, name, code)) {
|
| + if (target()->is_load_stub() || target()->is_store_stub()) {
|
| + if (UpdatePolymorphicIC(state, receiver, name, code, strict_mode)) {
|
| break;
|
| }
|
| CopyICToMegamorphicCache(name);
|
| UpdateMegamorphicCache(receiver->map(), *name, *code);
|
| - set_target(*megamorphic_stub());
|
| + set_target((strict_mode == kStrictMode)
|
| + ? *megamorphic_stub_strict()
|
| + : *megamorphic_stub());
|
| } else {
|
| // When trying to patch a polymorphic keyed load/store element stub
|
| // with anything other than another polymorphic stub, go generic.
|
|
|