Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(14)

Side by Side Diff: src/ic.h

Issue 400523007: Cache IC handlers on the prototype's map if possible (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: addressed comment Created 6 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/ia32/stub-cache-ia32.cc ('k') | src/ic.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 #ifndef V8_IC_H_ 5 #ifndef V8_IC_H_
6 #define V8_IC_H_ 6 #define V8_IC_H_
7 7
8 #include "src/macro-assembler.h" 8 #include "src/macro-assembler.h"
9 9
10 namespace v8 { 10 namespace v8 {
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
68 // JavaScript frames on the stack. 68 // JavaScript frames on the stack.
69 IC(FrameDepth depth, Isolate* isolate); 69 IC(FrameDepth depth, Isolate* isolate);
70 virtual ~IC() {} 70 virtual ~IC() {}
71 71
72 State state() const { return state_; } 72 State state() const { return state_; }
73 inline Address address() const; 73 inline Address address() const;
74 74
75 // Compute the current IC state based on the target stub, receiver and name. 75 // Compute the current IC state based on the target stub, receiver and name.
76 void UpdateState(Handle<Object> receiver, Handle<Object> name); 76 void UpdateState(Handle<Object> receiver, Handle<Object> name);
77 77
78 bool IsNameCompatibleWithMonomorphicPrototypeFailure(Handle<Object> name); 78 bool IsNameCompatibleWithPrototypeFailure(Handle<Object> name);
79 bool TryMarkMonomorphicPrototypeFailure(Handle<Object> name) { 79 void MarkPrototypeFailure(Handle<Object> name) {
80 if (IsNameCompatibleWithMonomorphicPrototypeFailure(name)) { 80 ASSERT(IsNameCompatibleWithPrototypeFailure(name));
81 state_ = MONOMORPHIC_PROTOTYPE_FAILURE; 81 state_ = PROTOTYPE_FAILURE;
82 return true;
83 }
84 return false;
85 } 82 }
86 83
87 // If the stub contains weak maps then this function adds the stub to 84 // If the stub contains weak maps then this function adds the stub to
88 // the dependent code array of each weak map. 85 // the dependent code array of each weak map.
89 static void RegisterWeakMapDependency(Handle<Code> stub); 86 static void RegisterWeakMapDependency(Handle<Code> stub);
90 87
91 // This function is called when a weak map in the stub is dying, 88 // This function is called when a weak map in the stub is dying,
92 // invalidates the stub by setting maps in it to undefined. 89 // invalidates the stub by setting maps in it to undefined.
93 static void InvalidateMaps(Code* stub); 90 static void InvalidateMaps(Code* stub);
94 91
95 // Clear the inline cache to initial state. 92 // Clear the inline cache to initial state.
96 static void Clear(Isolate* isolate, 93 static void Clear(Isolate* isolate,
97 Address address, 94 Address address,
98 ConstantPoolArray* constant_pool); 95 ConstantPoolArray* constant_pool);
99 96
100 #ifdef DEBUG 97 #ifdef DEBUG
101 bool IsLoadStub() const { 98 bool IsLoadStub() const {
102 return target()->is_load_stub() || target()->is_keyed_load_stub(); 99 return target()->is_load_stub() || target()->is_keyed_load_stub();
103 } 100 }
104 101
105 bool IsStoreStub() const { 102 bool IsStoreStub() const {
106 return target()->is_store_stub() || target()->is_keyed_store_stub(); 103 return target()->is_store_stub() || target()->is_keyed_store_stub();
107 } 104 }
108 105
109 bool IsCallStub() const { 106 bool IsCallStub() const {
110 return target()->is_call_stub(); 107 return target()->is_call_stub();
111 } 108 }
112 #endif 109 #endif
113 110
114 // Determines which map must be used for keeping the code stub. 111 template <class TypeClass>
115 // These methods should not be called with undefined or null. 112 static JSFunction* GetRootConstructor(TypeClass* type,
116 static inline InlineCacheHolderFlag GetCodeCacheForObject(Object* object); 113 Context* native_context);
117 // TODO(verwaest): This currently returns a HeapObject rather than JSObject* 114 static inline Handle<Map> GetHandlerCacheHolder(HeapType* type,
118 // since loading the IC for loading the length from strings are stored on 115 bool receiver_is_holder,
119 // the string map directly, rather than on the JSObject-typed prototype. 116 Isolate* isolate,
120 static inline HeapObject* GetCodeCacheHolder(Isolate* isolate, 117 CacheHolderFlag* flag);
121 Object* object, 118 static inline Handle<Map> GetICCacheHolder(HeapType* type, Isolate* isolate,
122 InlineCacheHolderFlag holder); 119 CacheHolderFlag* flag);
123
124 static inline InlineCacheHolderFlag GetCodeCacheFlag(HeapType* type);
125 static inline Handle<Map> GetCodeCacheHolder(InlineCacheHolderFlag flag,
126 HeapType* type,
127 Isolate* isolate);
128 120
129 static bool IsCleared(Code* code) { 121 static bool IsCleared(Code* code) {
130 InlineCacheState state = code->ic_state(); 122 InlineCacheState state = code->ic_state();
131 return state == UNINITIALIZED || state == PREMONOMORPHIC; 123 return state == UNINITIALIZED || state == PREMONOMORPHIC;
132 } 124 }
133 125
134 // Utility functions to convert maps to types and back. There are two special 126 // Utility functions to convert maps to types and back. There are two special
135 // cases: 127 // cases:
136 // - The heap_number_map is used as a marker which includes heap numbers as 128 // - The heap_number_map is used as a marker which includes heap numbers as
137 // well as smis. 129 // well as smis.
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
186 ConstantPoolArray* constant_pool); 178 ConstantPoolArray* constant_pool);
187 static void PostPatching(Address address, Code* target, Code* old_target); 179 static void PostPatching(Address address, Code* target, Code* old_target);
188 180
189 // Compute the handler either by compiling or by retrieving a cached version. 181 // Compute the handler either by compiling or by retrieving a cached version.
190 Handle<Code> ComputeHandler(LookupResult* lookup, 182 Handle<Code> ComputeHandler(LookupResult* lookup,
191 Handle<Object> object, 183 Handle<Object> object,
192 Handle<String> name, 184 Handle<String> name,
193 Handle<Object> value = Handle<Code>::null()); 185 Handle<Object> value = Handle<Code>::null());
194 virtual Handle<Code> CompileHandler(LookupResult* lookup, 186 virtual Handle<Code> CompileHandler(LookupResult* lookup,
195 Handle<Object> object, 187 Handle<Object> object,
196 Handle<String> name, 188 Handle<String> name, Handle<Object> value,
197 Handle<Object> value, 189 CacheHolderFlag cache_holder) {
198 InlineCacheHolderFlag cache_holder) {
199 UNREACHABLE(); 190 UNREACHABLE();
200 return Handle<Code>::null(); 191 return Handle<Code>::null();
201 } 192 }
202 193
203 void UpdateMonomorphicIC(Handle<HeapType> type, 194 void UpdateMonomorphicIC(Handle<Code> handler, Handle<String> name);
204 Handle<Code> handler,
205 Handle<String> name);
206 195
207 bool UpdatePolymorphicIC(Handle<HeapType> type, 196 bool UpdatePolymorphicIC(Handle<String> name, Handle<Code> code);
208 Handle<String> name,
209 Handle<Code> code);
210 197
211 virtual void UpdateMegamorphicCache(HeapType* type, Name* name, Code* code); 198 virtual void UpdateMegamorphicCache(HeapType* type, Name* name, Code* code);
212 199
213 void CopyICToMegamorphicCache(Handle<String> name); 200 void CopyICToMegamorphicCache(Handle<String> name);
214 bool IsTransitionOfMonomorphicTarget(Map* source_map, Map* target_map); 201 bool IsTransitionOfMonomorphicTarget(Map* source_map, Map* target_map);
215 void PatchCache(Handle<HeapType> type, 202 void PatchCache(Handle<String> name, Handle<Code> code);
216 Handle<String> name,
217 Handle<Code> code);
218 virtual Code::Kind kind() const { 203 virtual Code::Kind kind() const {
219 UNREACHABLE(); 204 UNREACHABLE();
220 return Code::STUB; 205 return Code::STUB;
221 } 206 }
222 virtual Handle<Code> slow_stub() const { 207 virtual Handle<Code> slow_stub() const {
223 UNREACHABLE(); 208 UNREACHABLE();
224 return Handle<Code>::null(); 209 return Handle<Code>::null();
225 } 210 }
226 virtual Handle<Code> megamorphic_stub() { 211 virtual Handle<Code> megamorphic_stub() {
227 UNREACHABLE(); 212 UNREACHABLE();
228 return Handle<Code>::null(); 213 return Handle<Code>::null();
229 } 214 }
230 virtual Handle<Code> generic_stub() const { 215 virtual Handle<Code> generic_stub() const {
231 UNREACHABLE(); 216 UNREACHABLE();
232 return Handle<Code>::null(); 217 return Handle<Code>::null();
233 } 218 }
234 219
235 bool TryRemoveInvalidPrototypeDependentStub(Handle<Object> receiver, 220 bool TryRemoveInvalidPrototypeDependentStub(Handle<Object> receiver,
236 Handle<String> name); 221 Handle<String> name);
237 void TryRemoveInvalidHandlers(Handle<Map> map, Handle<String> name);
238 222
239 ExtraICState extra_ic_state() const { return extra_ic_state_; } 223 ExtraICState extra_ic_state() const { return extra_ic_state_; }
240 void set_extra_ic_state(ExtraICState state) { 224 void set_extra_ic_state(ExtraICState state) {
241 extra_ic_state_ = state; 225 extra_ic_state_ = state;
242 } 226 }
243 227
228 Handle<HeapType> receiver_type() { return receiver_type_; }
229
244 void TargetMaps(MapHandleList* list) { 230 void TargetMaps(MapHandleList* list) {
245 FindTargetMaps(); 231 FindTargetMaps();
246 for (int i = 0; i < target_maps_.length(); i++) { 232 for (int i = 0; i < target_maps_.length(); i++) {
247 list->Add(target_maps_.at(i)); 233 list->Add(target_maps_.at(i));
248 } 234 }
249 } 235 }
250 236
251 void TargetTypes(TypeHandleList* list) { 237 void TargetTypes(TypeHandleList* list) {
252 FindTargetMaps(); 238 FindTargetMaps();
253 for (int i = 0; i < target_maps_.length(); i++) { 239 for (int i = 0; i < target_maps_.length(); i++) {
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
293 Address* pc_address_; 279 Address* pc_address_;
294 280
295 Isolate* isolate_; 281 Isolate* isolate_;
296 282
297 // The constant pool of the code which originally called the IC (which might 283 // The constant pool of the code which originally called the IC (which might
298 // be for the breakpointed copy of the original code). 284 // be for the breakpointed copy of the original code).
299 Handle<ConstantPoolArray> raw_constant_pool_; 285 Handle<ConstantPoolArray> raw_constant_pool_;
300 286
301 // The original code target that missed. 287 // The original code target that missed.
302 Handle<Code> target_; 288 Handle<Code> target_;
289 bool target_set_;
303 State state_; 290 State state_;
304 bool target_set_; 291 Handle<HeapType> receiver_type_;
292 MaybeHandle<Code> maybe_handler_;
305 293
306 ExtraICState extra_ic_state_; 294 ExtraICState extra_ic_state_;
307 MapHandleList target_maps_; 295 MapHandleList target_maps_;
308 bool target_maps_set_; 296 bool target_maps_set_;
309 297
310 DISALLOW_IMPLICIT_CONSTRUCTORS(IC); 298 DISALLOW_IMPLICIT_CONSTRUCTORS(IC);
311 }; 299 };
312 300
313 301
314 // An IC_Utility encapsulates IC::UtilityId. It exists mainly because you 302 // An IC_Utility encapsulates IC::UtilityId. It exists mainly because you
(...skipping 154 matching lines...) Expand 10 before | Expand all | Expand 10 after
469 // Update the inline cache and the global stub cache based on the 457 // Update the inline cache and the global stub cache based on the
470 // lookup result. 458 // lookup result.
471 void UpdateCaches(LookupResult* lookup, 459 void UpdateCaches(LookupResult* lookup,
472 Handle<Object> object, 460 Handle<Object> object,
473 Handle<String> name); 461 Handle<String> name);
474 462
475 virtual Handle<Code> CompileHandler(LookupResult* lookup, 463 virtual Handle<Code> CompileHandler(LookupResult* lookup,
476 Handle<Object> object, 464 Handle<Object> object,
477 Handle<String> name, 465 Handle<String> name,
478 Handle<Object> unused, 466 Handle<Object> unused,
479 InlineCacheHolderFlag cache_holder); 467 CacheHolderFlag cache_holder);
480 468
481 private: 469 private:
482 // Stub accessors. 470 // Stub accessors.
483 static Handle<Code> pre_monomorphic_stub(Isolate* isolate, 471 static Handle<Code> pre_monomorphic_stub(Isolate* isolate,
484 ExtraICState exstra_state); 472 ExtraICState exstra_state);
485 473
486 virtual Handle<Code> pre_monomorphic_stub() { 474 virtual Handle<Code> pre_monomorphic_stub() {
487 return pre_monomorphic_stub(isolate(), extra_ic_state()); 475 return pre_monomorphic_stub(isolate(), extra_ic_state());
488 } 476 }
489 477
(...skipping 153 matching lines...) Expand 10 before | Expand all | Expand 10 after
643 StrictMode strict_mode); 631 StrictMode strict_mode);
644 632
645 // Update the inline cache and the global stub cache based on the 633 // Update the inline cache and the global stub cache based on the
646 // lookup result. 634 // lookup result.
647 void UpdateCaches(LookupResult* lookup, 635 void UpdateCaches(LookupResult* lookup,
648 Handle<JSObject> receiver, 636 Handle<JSObject> receiver,
649 Handle<String> name, 637 Handle<String> name,
650 Handle<Object> value); 638 Handle<Object> value);
651 virtual Handle<Code> CompileHandler(LookupResult* lookup, 639 virtual Handle<Code> CompileHandler(LookupResult* lookup,
652 Handle<Object> object, 640 Handle<Object> object,
653 Handle<String> name, 641 Handle<String> name, Handle<Object> value,
654 Handle<Object> value, 642 CacheHolderFlag cache_holder);
655 InlineCacheHolderFlag cache_holder);
656 643
657 private: 644 private:
658 void set_target(Code* code) { 645 void set_target(Code* code) {
659 // Strict mode must be preserved across IC patching. 646 // Strict mode must be preserved across IC patching.
660 ASSERT(GetStrictMode(code->extra_ic_state()) == 647 ASSERT(GetStrictMode(code->extra_ic_state()) ==
661 GetStrictMode(target()->extra_ic_state())); 648 GetStrictMode(target()->extra_ic_state()));
662 IC::set_target(code); 649 IC::set_target(code);
663 } 650 }
664 651
665 static void Clear(Isolate* isolate, 652 static void Clear(Isolate* isolate,
(...skipping 377 matching lines...) Expand 10 before | Expand all | Expand 10 after
1043 DECLARE_RUNTIME_FUNCTION(ElementsTransitionAndStoreIC_Miss); 1030 DECLARE_RUNTIME_FUNCTION(ElementsTransitionAndStoreIC_Miss);
1044 DECLARE_RUNTIME_FUNCTION(BinaryOpIC_Miss); 1031 DECLARE_RUNTIME_FUNCTION(BinaryOpIC_Miss);
1045 DECLARE_RUNTIME_FUNCTION(BinaryOpIC_MissWithAllocationSite); 1032 DECLARE_RUNTIME_FUNCTION(BinaryOpIC_MissWithAllocationSite);
1046 DECLARE_RUNTIME_FUNCTION(CompareNilIC_Miss); 1033 DECLARE_RUNTIME_FUNCTION(CompareNilIC_Miss);
1047 DECLARE_RUNTIME_FUNCTION(ToBooleanIC_Miss); 1034 DECLARE_RUNTIME_FUNCTION(ToBooleanIC_Miss);
1048 1035
1049 1036
1050 } } // namespace v8::internal 1037 } } // namespace v8::internal
1051 1038
1052 #endif // V8_IC_H_ 1039 #endif // V8_IC_H_
OLDNEW
« no previous file with comments | « src/ia32/stub-cache-ia32.cc ('k') | src/ic.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698