| Index: src/type-feedback-vector.cc
|
| diff --git a/src/type-feedback-vector.cc b/src/type-feedback-vector.cc
|
| index 55ac5cfe7a8c020206097982a6d4d917a23563ea..adf0a5078af05c056bc1e765bd87f25a008f3357 100644
|
| --- a/src/type-feedback-vector.cc
|
| +++ b/src/type-feedback-vector.cc
|
| @@ -211,9 +211,15 @@ void TypeFeedbackVector::ClearICSlotsImpl(SharedFunctionInfo* shared,
|
| } else if (kind == Code::KEYED_LOAD_IC) {
|
| KeyedLoadICNexus nexus(this, slot);
|
| nexus.Clear(host);
|
| + } else if (kind == Code::STORE_IC) {
|
| + DCHECK(FLAG_vector_stores);
|
| + StoreICNexus nexus(this, slot);
|
| + nexus.Clear(host);
|
| + } else if (kind == Code::KEYED_STORE_IC) {
|
| + DCHECK(FLAG_vector_stores);
|
| + KeyedStoreICNexus nexus(this, slot);
|
| + nexus.Clear(host);
|
| }
|
| - // TODO(mvstanton): Handle clearing of store ics when FLAG_vector_stores
|
| - // is true.
|
| }
|
| }
|
| }
|
| @@ -258,6 +264,31 @@ void FeedbackNexus::InstallHandlers(Handle<FixedArray> array,
|
| }
|
|
|
|
|
| +void FeedbackNexus::ConfigureUninitialized() {
|
| + SetFeedback(*TypeFeedbackVector::UninitializedSentinel(GetIsolate()),
|
| + SKIP_WRITE_BARRIER);
|
| + SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(GetIsolate()),
|
| + SKIP_WRITE_BARRIER);
|
| +}
|
| +
|
| +
|
| +void FeedbackNexus::ConfigurePremonomorphic() {
|
| + SetFeedback(*TypeFeedbackVector::PremonomorphicSentinel(GetIsolate()),
|
| + SKIP_WRITE_BARRIER);
|
| + SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(GetIsolate()),
|
| + SKIP_WRITE_BARRIER);
|
| +}
|
| +
|
| +
|
| +void FeedbackNexus::ConfigureMegamorphic() {
|
| + Isolate* isolate = GetIsolate();
|
| + SetFeedback(*TypeFeedbackVector::MegamorphicSentinel(isolate),
|
| + SKIP_WRITE_BARRIER);
|
| + SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(isolate),
|
| + SKIP_WRITE_BARRIER);
|
| +}
|
| +
|
| +
|
| InlineCacheState LoadICNexus::StateFromFeedback() const {
|
| Isolate* isolate = GetIsolate();
|
| Object* feedback = GetFeedback();
|
| @@ -308,6 +339,56 @@ InlineCacheState KeyedLoadICNexus::StateFromFeedback() const {
|
| }
|
|
|
|
|
| +InlineCacheState StoreICNexus::StateFromFeedback() const {
|
| + Isolate* isolate = GetIsolate();
|
| + Object* feedback = GetFeedback();
|
| +
|
| + if (feedback == *TypeFeedbackVector::UninitializedSentinel(isolate)) {
|
| + return UNINITIALIZED;
|
| + } else if (feedback == *TypeFeedbackVector::MegamorphicSentinel(isolate)) {
|
| + return MEGAMORPHIC;
|
| + } else if (feedback == *TypeFeedbackVector::PremonomorphicSentinel(isolate)) {
|
| + return PREMONOMORPHIC;
|
| + } else if (feedback->IsFixedArray()) {
|
| + // Determine state purely by our structure, don't check if the maps are
|
| + // cleared.
|
| + return POLYMORPHIC;
|
| + } else if (feedback->IsWeakCell()) {
|
| + // Don't check if the map is cleared.
|
| + return MONOMORPHIC;
|
| + }
|
| +
|
| + return UNINITIALIZED;
|
| +}
|
| +
|
| +
|
| +InlineCacheState KeyedStoreICNexus::StateFromFeedback() const {
|
| + Isolate* isolate = GetIsolate();
|
| + Object* feedback = GetFeedback();
|
| +
|
| + if (feedback == *TypeFeedbackVector::UninitializedSentinel(isolate)) {
|
| + return UNINITIALIZED;
|
| + } else if (feedback == *TypeFeedbackVector::PremonomorphicSentinel(isolate)) {
|
| + return PREMONOMORPHIC;
|
| + } else if (feedback == *TypeFeedbackVector::MegamorphicSentinel(isolate)) {
|
| + return MEGAMORPHIC;
|
| + } else if (feedback->IsFixedArray()) {
|
| + // Determine state purely by our structure, don't check if the maps are
|
| + // cleared.
|
| + return POLYMORPHIC;
|
| + } else if (feedback->IsWeakCell()) {
|
| + // Don't check if the map is cleared.
|
| + return MONOMORPHIC;
|
| + } else if (feedback->IsName()) {
|
| + Object* extra = GetFeedbackExtra();
|
| + FixedArray* extra_array = FixedArray::cast(extra);
|
| + return extra_array->length() > 2 ? POLYMORPHIC : MONOMORPHIC;
|
| + }
|
| +
|
| + return UNINITIALIZED;
|
| +}
|
| +
|
| +
|
| InlineCacheState CallICNexus::StateFromFeedback() const {
|
| Isolate* isolate = GetIsolate();
|
| Object* feedback = GetFeedback();
|
| @@ -339,14 +420,6 @@ int CallICNexus::ExtractCallCount() {
|
| void CallICNexus::Clear(Code* host) { CallIC::Clear(GetIsolate(), host, this); }
|
|
|
|
|
| -void CallICNexus::ConfigureGeneric() {
|
| - SetFeedback(*TypeFeedbackVector::MegamorphicSentinel(GetIsolate()),
|
| - SKIP_WRITE_BARRIER);
|
| - SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(GetIsolate()),
|
| - SKIP_WRITE_BARRIER);
|
| -}
|
| -
|
| -
|
| void CallICNexus::ConfigureMonomorphicArray() {
|
| Object* feedback = GetFeedback();
|
| if (!feedback->IsAllocationSite()) {
|
| @@ -358,14 +431,6 @@ void CallICNexus::ConfigureMonomorphicArray() {
|
| }
|
|
|
|
|
| -void CallICNexus::ConfigureUninitialized() {
|
| - SetFeedback(*TypeFeedbackVector::UninitializedSentinel(GetIsolate()),
|
| - SKIP_WRITE_BARRIER);
|
| - SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(GetIsolate()),
|
| - SKIP_WRITE_BARRIER);
|
| -}
|
| -
|
| -
|
| void CallICNexus::ConfigureMonomorphic(Handle<JSFunction> function) {
|
| Handle<WeakCell> new_cell = GetIsolate()->factory()->NewWeakCell(function);
|
| SetFeedback(*new_cell);
|
| @@ -373,51 +438,41 @@ void CallICNexus::ConfigureMonomorphic(Handle<JSFunction> function) {
|
| }
|
|
|
|
|
| -void KeyedLoadICNexus::ConfigureMegamorphic() {
|
| - Isolate* isolate = GetIsolate();
|
| - SetFeedback(*TypeFeedbackVector::MegamorphicSentinel(isolate),
|
| - SKIP_WRITE_BARRIER);
|
| - SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(isolate),
|
| - SKIP_WRITE_BARRIER);
|
| -}
|
| -
|
| -
|
| -void LoadICNexus::ConfigureMegamorphic() {
|
| - SetFeedback(*TypeFeedbackVector::MegamorphicSentinel(GetIsolate()),
|
| - SKIP_WRITE_BARRIER);
|
| - SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(GetIsolate()),
|
| - SKIP_WRITE_BARRIER);
|
| -}
|
| -
|
| -
|
| -void LoadICNexus::ConfigurePremonomorphic() {
|
| - SetFeedback(*TypeFeedbackVector::PremonomorphicSentinel(GetIsolate()),
|
| - SKIP_WRITE_BARRIER);
|
| - SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(GetIsolate()),
|
| - SKIP_WRITE_BARRIER);
|
| +void LoadICNexus::ConfigureMonomorphic(Handle<Map> receiver_map,
|
| + Handle<Code> handler) {
|
| + Handle<WeakCell> cell = Map::WeakCellForMap(receiver_map);
|
| + SetFeedback(*cell);
|
| + SetFeedbackExtra(*handler);
|
| }
|
|
|
|
|
| -void KeyedLoadICNexus::ConfigurePremonomorphic() {
|
| - Isolate* isolate = GetIsolate();
|
| - SetFeedback(*TypeFeedbackVector::PremonomorphicSentinel(isolate),
|
| - SKIP_WRITE_BARRIER);
|
| - SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(isolate),
|
| - SKIP_WRITE_BARRIER);
|
| +void KeyedLoadICNexus::ConfigureMonomorphic(Handle<Name> name,
|
| + Handle<Map> receiver_map,
|
| + Handle<Code> handler) {
|
| + Handle<WeakCell> cell = Map::WeakCellForMap(receiver_map);
|
| + if (name.is_null()) {
|
| + SetFeedback(*cell);
|
| + SetFeedbackExtra(*handler);
|
| + } else {
|
| + SetFeedback(*name);
|
| + Handle<FixedArray> array = EnsureExtraArrayOfSize(2);
|
| + array->set(0, *cell);
|
| + array->set(1, *handler);
|
| + }
|
| }
|
|
|
|
|
| -void LoadICNexus::ConfigureMonomorphic(Handle<Map> receiver_map,
|
| - Handle<Code> handler) {
|
| +void StoreICNexus::ConfigureMonomorphic(Handle<Map> receiver_map,
|
| + Handle<Code> handler) {
|
| Handle<WeakCell> cell = Map::WeakCellForMap(receiver_map);
|
| SetFeedback(*cell);
|
| SetFeedbackExtra(*handler);
|
| }
|
|
|
|
|
| -void KeyedLoadICNexus::ConfigureMonomorphic(Handle<Name> name,
|
| - Handle<Map> receiver_map,
|
| - Handle<Code> handler) {
|
| +void KeyedStoreICNexus::ConfigureMonomorphic(Handle<Name> name,
|
| + Handle<Map> receiver_map,
|
| + Handle<Code> handler) {
|
| Handle<WeakCell> cell = Map::WeakCellForMap(receiver_map);
|
| if (name.is_null()) {
|
| SetFeedback(*cell);
|
| @@ -461,6 +516,36 @@ void KeyedLoadICNexus::ConfigurePolymorphic(Handle<Name> name,
|
| }
|
|
|
|
|
| +void StoreICNexus::ConfigurePolymorphic(MapHandleList* maps,
|
| + CodeHandleList* handlers) {
|
| + Isolate* isolate = GetIsolate();
|
| + int receiver_count = maps->length();
|
| + Handle<FixedArray> array = EnsureArrayOfSize(receiver_count * 2);
|
| + InstallHandlers(array, maps, handlers);
|
| + SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(isolate),
|
| + SKIP_WRITE_BARRIER);
|
| +}
|
| +
|
| +
|
| +void KeyedStoreICNexus::ConfigurePolymorphic(Handle<Name> name,
|
| + MapHandleList* maps,
|
| + CodeHandleList* handlers) {
|
| + int receiver_count = maps->length();
|
| + DCHECK(receiver_count > 1);
|
| + Handle<FixedArray> array;
|
| + if (name.is_null()) {
|
| + array = EnsureArrayOfSize(receiver_count * 2);
|
| + SetFeedbackExtra(*TypeFeedbackVector::UninitializedSentinel(GetIsolate()),
|
| + SKIP_WRITE_BARRIER);
|
| + } else {
|
| + SetFeedback(*name);
|
| + array = EnsureExtraArrayOfSize(receiver_count * 2);
|
| + }
|
| +
|
| + InstallHandlers(array, maps, handlers);
|
| +}
|
| +
|
| +
|
| int FeedbackNexus::ExtractMaps(MapHandleList* maps) const {
|
| Isolate* isolate = GetIsolate();
|
| Object* feedback = GetFeedback();
|
| @@ -580,5 +665,24 @@ Name* KeyedLoadICNexus::FindFirstName() const {
|
| }
|
| return NULL;
|
| }
|
| +
|
| +
|
| +Name* KeyedStoreICNexus::FindFirstName() const {
|
| + Object* feedback = GetFeedback();
|
| + if (feedback->IsString()) {
|
| + return Name::cast(feedback);
|
| + }
|
| + return NULL;
|
| +}
|
| +
|
| +
|
| +void StoreICNexus::Clear(Code* host) {
|
| + StoreIC::Clear(GetIsolate(), host, this);
|
| +}
|
| +
|
| +
|
| +void KeyedStoreICNexus::Clear(Code* host) {
|
| + KeyedStoreIC::Clear(GetIsolate(), host, this);
|
| +}
|
| } // namespace internal
|
| } // namespace v8
|
|
|