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 342 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
353 | 353 |
354 Reduction JSNativeContextSpecialization::ReduceJSLoadNamed(Node* node) { | 354 Reduction JSNativeContextSpecialization::ReduceJSLoadNamed(Node* node) { |
355 DCHECK_EQ(IrOpcode::kJSLoadNamed, node->opcode()); | 355 DCHECK_EQ(IrOpcode::kJSLoadNamed, node->opcode()); |
356 NamedAccess const& p = NamedAccessOf(node->op()); | 356 NamedAccess const& p = NamedAccessOf(node->op()); |
357 Node* const receiver = NodeProperties::GetValueInput(node, 0); | 357 Node* const receiver = NodeProperties::GetValueInput(node, 0); |
358 Node* const value = jsgraph()->Dead(); | 358 Node* const value = jsgraph()->Dead(); |
359 | 359 |
360 // Check if we have a constant receiver. | 360 // Check if we have a constant receiver. |
361 HeapObjectMatcher m(receiver); | 361 HeapObjectMatcher m(receiver); |
362 if (m.HasValue()) { | 362 if (m.HasValue()) { |
363 // Optimize "prototype" property of functions. | |
364 if (m.Value()->IsJSFunction() && | 363 if (m.Value()->IsJSFunction() && |
365 p.name().is_identical_to(factory()->prototype_string())) { | 364 p.name().is_identical_to(factory()->prototype_string())) { |
| 365 // Optimize "prototype" property of functions. |
366 Handle<JSFunction> function = Handle<JSFunction>::cast(m.Value()); | 366 Handle<JSFunction> function = Handle<JSFunction>::cast(m.Value()); |
367 if (function->has_initial_map()) { | 367 if (function->has_initial_map()) { |
368 // We need to add a code dependency on the initial map of the | 368 // We need to add a code dependency on the initial map of the |
369 // {function} in order to be notified about changes to the | 369 // {function} in order to be notified about changes to the |
370 // "prototype" of {function}, so it doesn't make sense to | 370 // "prototype" of {function}, so it doesn't make sense to |
371 // continue unless deoptimization is enabled. | 371 // continue unless deoptimization is enabled. |
372 if (flags() & kDeoptimizationEnabled) { | 372 if (flags() & kDeoptimizationEnabled) { |
373 Handle<Map> initial_map(function->initial_map(), isolate()); | 373 Handle<Map> initial_map(function->initial_map(), isolate()); |
374 dependencies()->AssumeInitialMapCantChange(initial_map); | 374 dependencies()->AssumeInitialMapCantChange(initial_map); |
375 Handle<Object> prototype(initial_map->prototype(), isolate()); | 375 Handle<Object> prototype(initial_map->prototype(), isolate()); |
376 Node* value = jsgraph()->Constant(prototype); | 376 Node* value = jsgraph()->Constant(prototype); |
377 ReplaceWithValue(node, value); | 377 ReplaceWithValue(node, value); |
378 return Replace(value); | 378 return Replace(value); |
379 } | 379 } |
380 } | 380 } |
| 381 } else if (m.Value()->IsString() && |
| 382 p.name().is_identical_to(factory()->length_string())) { |
| 383 // Constant-fold "length" property on constant strings. |
| 384 Handle<String> string = Handle<String>::cast(m.Value()); |
| 385 Node* value = jsgraph()->Constant(string->length()); |
| 386 ReplaceWithValue(node, value); |
| 387 return Replace(value); |
381 } | 388 } |
382 } | 389 } |
383 | 390 |
384 // Extract receiver maps from the LOAD_IC using the LoadICNexus. | 391 // Extract receiver maps from the LOAD_IC using the LoadICNexus. |
385 if (!p.feedback().IsValid()) return NoChange(); | 392 if (!p.feedback().IsValid()) return NoChange(); |
386 LoadICNexus nexus(p.feedback().vector(), p.feedback().slot()); | 393 LoadICNexus nexus(p.feedback().vector(), p.feedback().slot()); |
387 | 394 |
388 // Try to lower the named access based on the {receiver_maps}. | 395 // Try to lower the named access based on the {receiver_maps}. |
389 return ReduceNamedAccessFromNexus(node, value, nexus, p.name(), | 396 return ReduceNamedAccessFromNexus(node, value, nexus, p.name(), |
390 AccessMode::kLoad, p.language_mode()); | 397 AccessMode::kLoad, p.language_mode()); |
(...skipping 1102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1493 return jsgraph()->javascript(); | 1500 return jsgraph()->javascript(); |
1494 } | 1501 } |
1495 | 1502 |
1496 SimplifiedOperatorBuilder* JSNativeContextSpecialization::simplified() const { | 1503 SimplifiedOperatorBuilder* JSNativeContextSpecialization::simplified() const { |
1497 return jsgraph()->simplified(); | 1504 return jsgraph()->simplified(); |
1498 } | 1505 } |
1499 | 1506 |
1500 } // namespace compiler | 1507 } // namespace compiler |
1501 } // namespace internal | 1508 } // namespace internal |
1502 } // namespace v8 | 1509 } // namespace v8 |
OLD | NEW |