OLD | NEW |
1 // Copyright 2015 the V8 project authors. All rights reserved. | 1 // Copyright 2015 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 #include "src/compiler/js-native-context-specialization.h" | 5 #include "src/compiler/js-native-context-specialization.h" |
6 | 6 |
7 #include "src/accessors.h" | 7 #include "src/accessors.h" |
8 #include "src/code-factory.h" | 8 #include "src/code-factory.h" |
9 #include "src/compilation-dependencies.h" | 9 #include "src/compilation-dependencies.h" |
10 #include "src/compiler/access-builder.h" | 10 #include "src/compiler/access-builder.h" |
(...skipping 555 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
566 | 566 |
567 // Check if we have an access o.x or o.x=v where o is the current | 567 // Check if we have an access o.x or o.x=v where o is the current |
568 // native contexts' global proxy, and turn that into a direct access | 568 // native contexts' global proxy, and turn that into a direct access |
569 // to the current native contexts' global object instead. | 569 // to the current native contexts' global object instead. |
570 if (receiver_maps.length() == 1) { | 570 if (receiver_maps.length() == 1) { |
571 Handle<Map> receiver_map = receiver_maps.first(); | 571 Handle<Map> receiver_map = receiver_maps.first(); |
572 if (receiver_map->IsJSGlobalProxyMap()) { | 572 if (receiver_map->IsJSGlobalProxyMap()) { |
573 Object* maybe_constructor = receiver_map->GetConstructor(); | 573 Object* maybe_constructor = receiver_map->GetConstructor(); |
574 // Detached global proxies have |null| as their constructor. | 574 // Detached global proxies have |null| as their constructor. |
575 if (maybe_constructor->IsJSFunction() && | 575 if (maybe_constructor->IsJSFunction() && |
576 JSFunction::cast(maybe_constructor)->has_context() && | |
577 JSFunction::cast(maybe_constructor)->native_context() == | 576 JSFunction::cast(maybe_constructor)->native_context() == |
578 *native_context()) { | 577 *native_context()) { |
579 return ReduceGlobalAccess(node, receiver, value, name, access_mode, | 578 return ReduceGlobalAccess(node, receiver, value, name, access_mode, |
580 index); | 579 index); |
581 } | 580 } |
582 } | 581 } |
583 } | 582 } |
584 | 583 |
585 // Compute property access infos for the receiver maps. | 584 // Compute property access infos for the receiver maps. |
586 AccessInfoFactory access_info_factory(dependencies(), native_context(), | 585 AccessInfoFactory access_info_factory(dependencies(), native_context(), |
(...skipping 206 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
793 | 792 |
794 if (flags() & kDeoptimizationEnabled) { | 793 if (flags() & kDeoptimizationEnabled) { |
795 // Check if we are accessing the current native contexts' global proxy. | 794 // Check if we are accessing the current native contexts' global proxy. |
796 HeapObjectMatcher m(receiver); | 795 HeapObjectMatcher m(receiver); |
797 if (m.HasValue() && m.Value().is_identical_to(global_proxy())) { | 796 if (m.HasValue() && m.Value().is_identical_to(global_proxy())) { |
798 // Optimize accesses to the current native contexts' global proxy. | 797 // Optimize accesses to the current native contexts' global proxy. |
799 return ReduceGlobalAccess(node, nullptr, value, name, access_mode); | 798 return ReduceGlobalAccess(node, nullptr, value, name, access_mode); |
800 } | 799 } |
801 } | 800 } |
802 | 801 |
| 802 // Check if the {nexus} reports type feedback for the IC. |
| 803 if (nexus.IsUninitialized()) { |
| 804 if ((flags() & kDeoptimizationEnabled) && |
| 805 (flags() & kBailoutOnUninitialized)) { |
| 806 return ReduceSoftDeoptimize( |
| 807 node, |
| 808 DeoptimizeReason::kInsufficientTypeFeedbackForGenericNamedAccess); |
| 809 } |
| 810 return NoChange(); |
| 811 } |
| 812 |
803 // Extract receiver maps from the IC using the {nexus}. | 813 // Extract receiver maps from the IC using the {nexus}. |
804 MapHandleList receiver_maps; | 814 MapHandleList receiver_maps; |
805 if (!ExtractReceiverMaps(receiver, effect, nexus, &receiver_maps)) { | 815 if (!ExtractReceiverMaps(receiver, effect, nexus, &receiver_maps)) { |
806 return NoChange(); | 816 return NoChange(); |
807 } else if (receiver_maps.length() == 0) { | 817 } else if (receiver_maps.length() == 0) { |
808 if ((flags() & kDeoptimizationEnabled) && | 818 if ((flags() & kDeoptimizationEnabled) && |
809 (flags() & kBailoutOnUninitialized)) { | 819 (flags() & kBailoutOnUninitialized)) { |
810 return ReduceSoftDeoptimize( | 820 return ReduceSoftDeoptimize( |
811 node, | 821 node, |
812 DeoptimizeReason::kInsufficientTypeFeedbackForGenericNamedAccess); | 822 DeoptimizeReason::kInsufficientTypeFeedbackForGenericNamedAccess); |
(...skipping 364 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1177 | 1187 |
1178 // Return the character from the {receiver} as single character string. | 1188 // Return the character from the {receiver} as single character string. |
1179 value = graph()->NewNode(simplified()->StringCharAt(), receiver, index, | 1189 value = graph()->NewNode(simplified()->StringCharAt(), receiver, index, |
1180 control); | 1190 control); |
1181 ReplaceWithValue(node, value, effect, control); | 1191 ReplaceWithValue(node, value, effect, control); |
1182 return Replace(value); | 1192 return Replace(value); |
1183 } | 1193 } |
1184 } | 1194 } |
1185 } | 1195 } |
1186 | 1196 |
| 1197 // Check if the {nexus} reports type feedback for the IC. |
| 1198 if (nexus.IsUninitialized()) { |
| 1199 if ((flags() & kDeoptimizationEnabled) && |
| 1200 (flags() & kBailoutOnUninitialized)) { |
| 1201 return ReduceSoftDeoptimize( |
| 1202 node, |
| 1203 DeoptimizeReason::kInsufficientTypeFeedbackForGenericKeyedAccess); |
| 1204 } |
| 1205 return NoChange(); |
| 1206 } |
| 1207 |
1187 // Extract receiver maps from the {nexus}. | 1208 // Extract receiver maps from the {nexus}. |
1188 MapHandleList receiver_maps; | 1209 MapHandleList receiver_maps; |
1189 if (!ExtractReceiverMaps(receiver, effect, nexus, &receiver_maps)) { | 1210 if (!ExtractReceiverMaps(receiver, effect, nexus, &receiver_maps)) { |
1190 return NoChange(); | 1211 return NoChange(); |
1191 } else if (receiver_maps.length() == 0) { | 1212 } else if (receiver_maps.length() == 0) { |
1192 if ((flags() & kDeoptimizationEnabled) && | 1213 if ((flags() & kDeoptimizationEnabled) && |
1193 (flags() & kBailoutOnUninitialized)) { | 1214 (flags() & kBailoutOnUninitialized)) { |
1194 return ReduceSoftDeoptimize( | 1215 return ReduceSoftDeoptimize( |
1195 node, | 1216 node, |
1196 DeoptimizeReason::kInsufficientTypeFeedbackForGenericKeyedAccess); | 1217 DeoptimizeReason::kInsufficientTypeFeedbackForGenericKeyedAccess); |
(...skipping 1025 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2222 Handle<Map> receiver_map; | 2243 Handle<Map> receiver_map; |
2223 if (InferReceiverRootMap(receiver).ToHandle(&receiver_map)) { | 2244 if (InferReceiverRootMap(receiver).ToHandle(&receiver_map)) { |
2224 for (int i = receiver_maps->length(); --i >= 0;) { | 2245 for (int i = receiver_maps->length(); --i >= 0;) { |
2225 if (receiver_maps->at(i)->FindRootMap() != *receiver_map) { | 2246 if (receiver_maps->at(i)->FindRootMap() != *receiver_map) { |
2226 receiver_maps->Remove(i); | 2247 receiver_maps->Remove(i); |
2227 } | 2248 } |
2228 } | 2249 } |
2229 } | 2250 } |
2230 return true; | 2251 return true; |
2231 } | 2252 } |
2232 // Check if the {nexus} actually reports feedback for the IC. We return | 2253 return false; |
2233 // true if the IC is still uninitialized, which translates to a SOFT | |
2234 // deoptimization exit in the callers. | |
2235 return nexus.IsUninitialized(); | |
2236 } | 2254 } |
2237 | 2255 |
2238 bool JSNativeContextSpecialization::InferReceiverMaps( | 2256 bool JSNativeContextSpecialization::InferReceiverMaps( |
2239 Node* receiver, Node* effect, MapHandleList* receiver_maps) { | 2257 Node* receiver, Node* effect, MapHandleList* receiver_maps) { |
2240 ZoneHandleSet<Map> maps; | 2258 ZoneHandleSet<Map> maps; |
2241 if (NodeProperties::InferReceiverMaps(receiver, effect, &maps)) { | 2259 if (NodeProperties::InferReceiverMaps(receiver, effect, &maps)) { |
2242 for (size_t i = 0; i < maps.size(); ++i) { | 2260 for (size_t i = 0; i < maps.size(); ++i) { |
2243 receiver_maps->Add(maps[i]); | 2261 receiver_maps->Add(maps[i]); |
2244 } | 2262 } |
2245 return true; | 2263 return true; |
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2312 return jsgraph()->javascript(); | 2330 return jsgraph()->javascript(); |
2313 } | 2331 } |
2314 | 2332 |
2315 SimplifiedOperatorBuilder* JSNativeContextSpecialization::simplified() const { | 2333 SimplifiedOperatorBuilder* JSNativeContextSpecialization::simplified() const { |
2316 return jsgraph()->simplified(); | 2334 return jsgraph()->simplified(); |
2317 } | 2335 } |
2318 | 2336 |
2319 } // namespace compiler | 2337 } // namespace compiler |
2320 } // namespace internal | 2338 } // namespace internal |
2321 } // namespace v8 | 2339 } // namespace v8 |
OLD | NEW |