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

Unified Diff: src/ic/ic.cc

Issue 2421883002: [ic] Support data handlers that represent loads of constants from prototypes. (Closed)
Patch Set: Created 4 years, 2 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/ic/ic.h ('k') | no next file » | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/ic/ic.cc
diff --git a/src/ic/ic.cc b/src/ic/ic.cc
index cfa740b1051c76355cec051a0e06665e6b1a44d7..d036b343d83c90b602686287c463bc4b6855b2e0 100644
--- a/src/ic/ic.cc
+++ b/src/ic/ic.cc
@@ -857,18 +857,15 @@ Handle<Object> LoadIC::SimpleFieldLoad(FieldIndex index) {
return stub.GetCode();
}
-Handle<Object> LoadIC::SimpleFieldLoadFromPrototype(FieldIndex index,
- Handle<Map> receiver_map,
- Handle<JSObject> holder) {
- if (!FLAG_tf_load_ic_stub) return Handle<Object>::null();
-
+bool LoadIC::IsPrototypeValidityCellCheckEnough(Handle<Map> receiver_map,
+ Handle<JSObject> holder) {
DCHECK(holder->HasFastProperties());
// The following kinds of receiver maps require custom handler compilation.
if (receiver_map->IsPrimitiveMap() || receiver_map->IsJSGlobalProxyMap() ||
receiver_map->IsJSGlobalObjectMap() ||
receiver_map->is_dictionary_map()) {
- return Handle<Object>::null();
+ return false;
}
// Switch to custom compiled handler if the prototype chain contains global
@@ -879,21 +876,27 @@ Handle<Object> LoadIC::SimpleFieldLoadFromPrototype(FieldIndex index,
Map* current_map = current->map();
if (current_map->IsJSGlobalObjectMap() ||
current_map->IsJSGlobalProxyMap() || current_map->is_dictionary_map()) {
- return Handle<Object>::null();
+ return false;
}
// Only objects that do not require access checks are allowed in stubs.
DCHECK(!current_map->is_access_check_needed());
}
- TRACE_HANDLER_STATS(isolate(), LoadIC_LoadFieldFromPrototypeDH);
+ return true;
+}
+
+Handle<Object> LoadIC::SimpleLoadFromPrototype(Handle<Map> receiver_map,
+ Handle<JSObject> holder,
+ Handle<Object> smi_handler) {
+ DCHECK(IsPrototypeValidityCellCheckEnough(receiver_map, holder));
+
Handle<Cell> validity_cell =
Map::GetOrCreatePrototypeChainValidityCell(receiver_map, isolate());
DCHECK(!validity_cell.is_null());
- Handle<Object> handler(SmiHandler::MakeLoadFieldHandler(isolate(), index));
Factory* factory = isolate()->factory();
Handle<WeakCell> holder_cell = factory->NewWeakCell(holder);
- return factory->NewTuple3(validity_cell, holder_cell, handler);
+ return factory->NewTuple3(validity_cell, holder_cell, smi_handler);
}
bool IsCompatibleReceiver(LookupIterator* lookup, Handle<Map> receiver_map) {
@@ -1196,28 +1199,37 @@ Handle<Object> LoadIC::GetMapIndependentHandler(LookupIterator* lookup) {
// -------------- Fields --------------
if (lookup->property_details().type() == DATA) {
FieldIndex field = lookup->GetFieldIndex();
+ Handle<Object> smi_handler = SimpleFieldLoad(field);
if (receiver_is_holder) {
- return SimpleFieldLoad(field);
+ return smi_handler;
}
- Handle<Object> handler =
- SimpleFieldLoadFromPrototype(field, map, holder);
- if (!handler.is_null()) {
- return handler;
+ if (FLAG_tf_load_ic_stub &&
+ IsPrototypeValidityCellCheckEnough(map, holder)) {
+ TRACE_HANDLER_STATS(isolate(), LoadIC_LoadFieldFromPrototypeDH);
+ return SimpleLoadFromPrototype(map, holder, smi_handler);
}
break; // Custom-compiled handler.
}
// -------------- Constant properties --------------
DCHECK(lookup->property_details().type() == DATA_CONSTANT);
- if (receiver_is_holder) {
- if (FLAG_tf_load_ic_stub) {
+ if (FLAG_tf_load_ic_stub) {
+ Handle<Object> smi_handler = SmiHandler::MakeLoadConstantHandler(
+ isolate(), lookup->GetConstantIndex());
+ if (receiver_is_holder) {
TRACE_HANDLER_STATS(isolate(), LoadIC_LoadConstantDH);
- return SmiHandler::MakeLoadConstantHandler(
- isolate(), lookup->GetConstantIndex());
+ return smi_handler;
+ }
+ if (IsPrototypeValidityCellCheckEnough(map, holder)) {
+ TRACE_HANDLER_STATS(isolate(), LoadIC_LoadConstantFromPrototypeDH);
+ return SimpleLoadFromPrototype(map, holder, smi_handler);
+ }
+ } else {
+ if (receiver_is_holder) {
+ TRACE_HANDLER_STATS(isolate(), LoadIC_LoadConstantStub);
+ LoadConstantStub stub(isolate(), lookup->GetConstantIndex());
+ return stub.GetCode();
}
- TRACE_HANDLER_STATS(isolate(), LoadIC_LoadConstantStub);
- LoadConstantStub stub(isolate(), lookup->GetConstantIndex());
- return stub.GetCode();
}
break; // Custom-compiled handler.
}
« no previous file with comments | « src/ic/ic.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698