OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 1372 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1383 | 1383 |
1384 | 1384 |
1385 HValue* HGraphBuilder::BuildCopyElementsOnWrite(HValue* object, | 1385 HValue* HGraphBuilder::BuildCopyElementsOnWrite(HValue* object, |
1386 HValue* elements, | 1386 HValue* elements, |
1387 ElementsKind kind, | 1387 ElementsKind kind, |
1388 HValue* length) { | 1388 HValue* length) { |
1389 Factory* factory = isolate()->factory(); | 1389 Factory* factory = isolate()->factory(); |
1390 | 1390 |
1391 IfBuilder cow_checker(this); | 1391 IfBuilder cow_checker(this); |
1392 | 1392 |
1393 cow_checker.If<HCompareMap>(elements, factory->fixed_cow_array_map()); | 1393 cow_checker.If<HCompareMap>( |
| 1394 elements, factory->fixed_cow_array_map(), top_info()); |
1394 cow_checker.Then(); | 1395 cow_checker.Then(); |
1395 | 1396 |
1396 HValue* capacity = AddLoadFixedArrayLength(elements); | 1397 HValue* capacity = AddLoadFixedArrayLength(elements); |
1397 | 1398 |
1398 HValue* new_elements = BuildGrowElementsCapacity(object, elements, kind, | 1399 HValue* new_elements = BuildGrowElementsCapacity(object, elements, kind, |
1399 kind, length, capacity); | 1400 kind, length, capacity); |
1400 | 1401 |
1401 environment()->Push(new_elements); | 1402 environment()->Push(new_elements); |
1402 | 1403 |
1403 cow_checker.Else(); | 1404 cow_checker.Else(); |
(...skipping 296 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1700 if_objectiskey.JoinContinuation(&found); | 1701 if_objectiskey.JoinContinuation(&found); |
1701 } | 1702 } |
1702 if_objectissmi.Else(); | 1703 if_objectissmi.Else(); |
1703 { | 1704 { |
1704 if (type->Is(Type::Smi())) { | 1705 if (type->Is(Type::Smi())) { |
1705 if_objectissmi.Deopt("Expected smi"); | 1706 if_objectissmi.Deopt("Expected smi"); |
1706 } else { | 1707 } else { |
1707 // Check if the object is a heap number. | 1708 // Check if the object is a heap number. |
1708 IfBuilder if_objectisnumber(this); | 1709 IfBuilder if_objectisnumber(this); |
1709 HValue* objectisnumber = if_objectisnumber.If<HCompareMap>( | 1710 HValue* objectisnumber = if_objectisnumber.If<HCompareMap>( |
1710 object, isolate()->factory()->heap_number_map()); | 1711 object, isolate()->factory()->heap_number_map(), top_info()); |
1711 if_objectisnumber.Then(); | 1712 if_objectisnumber.Then(); |
1712 { | 1713 { |
1713 // Compute hash for heap number similar to double_get_hash(). | 1714 // Compute hash for heap number similar to double_get_hash(). |
1714 HValue* low = Add<HLoadNamedField>( | 1715 HValue* low = Add<HLoadNamedField>( |
1715 object, objectisnumber, | 1716 object, objectisnumber, |
1716 HObjectAccess::ForHeapNumberValueLowestBits()); | 1717 HObjectAccess::ForHeapNumberValueLowestBits()); |
1717 HValue* high = Add<HLoadNamedField>( | 1718 HValue* high = Add<HLoadNamedField>( |
1718 object, objectisnumber, | 1719 object, objectisnumber, |
1719 HObjectAccess::ForHeapNumberValueHighestBits()); | 1720 HObjectAccess::ForHeapNumberValueHighestBits()); |
1720 HValue* hash = AddUncasted<HBitwise>(Token::BIT_XOR, low, high); | 1721 HValue* hash = AddUncasted<HBitwise>(Token::BIT_XOR, low, high); |
(...skipping 3923 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5644 } | 5645 } |
5645 } | 5646 } |
5646 ++count; | 5647 ++count; |
5647 HBasicBlock* if_true = graph()->CreateBasicBlock(); | 5648 HBasicBlock* if_true = graph()->CreateBasicBlock(); |
5648 HBasicBlock* if_false = graph()->CreateBasicBlock(); | 5649 HBasicBlock* if_false = graph()->CreateBasicBlock(); |
5649 HUnaryControlInstruction* compare; | 5650 HUnaryControlInstruction* compare; |
5650 | 5651 |
5651 HValue* dependency; | 5652 HValue* dependency; |
5652 if (info.type()->Is(Type::Number())) { | 5653 if (info.type()->Is(Type::Number())) { |
5653 Handle<Map> heap_number_map = isolate()->factory()->heap_number_map(); | 5654 Handle<Map> heap_number_map = isolate()->factory()->heap_number_map(); |
5654 compare = New<HCompareMap>(object, heap_number_map, if_true, if_false); | 5655 compare = New<HCompareMap>(object, heap_number_map, top_info(), |
| 5656 if_true, if_false); |
5655 dependency = smi_check; | 5657 dependency = smi_check; |
5656 } else if (info.type()->Is(Type::String())) { | 5658 } else if (info.type()->Is(Type::String())) { |
5657 compare = New<HIsStringAndBranch>(object, if_true, if_false); | 5659 compare = New<HIsStringAndBranch>(object, if_true, if_false); |
5658 dependency = compare; | 5660 dependency = compare; |
5659 } else { | 5661 } else { |
5660 compare = New<HCompareMap>(object, info.map(), if_true, if_false); | 5662 compare = New<HCompareMap>(object, info.map(), top_info(), |
| 5663 if_true, if_false); |
5661 dependency = compare; | 5664 dependency = compare; |
5662 } | 5665 } |
5663 FinishCurrentBlock(compare); | 5666 FinishCurrentBlock(compare); |
5664 | 5667 |
5665 if (info.type()->Is(Type::Number())) { | 5668 if (info.type()->Is(Type::Number())) { |
5666 Goto(if_true, number_block); | 5669 Goto(if_true, number_block); |
5667 if_true = number_block; | 5670 if_true = number_block; |
5668 number_block->SetJoinId(ast_id); | 5671 number_block->SetJoinId(ast_id); |
5669 } | 5672 } |
5670 | 5673 |
(...skipping 619 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6290 // Remember the most general elements kind, the code for its load will | 6293 // Remember the most general elements kind, the code for its load will |
6291 // properly handle all of the more specific cases. | 6294 // properly handle all of the more specific cases. |
6292 if ((i == 0) || IsMoreGeneralElementsKindTransition( | 6295 if ((i == 0) || IsMoreGeneralElementsKindTransition( |
6293 most_general_consolidated_map->elements_kind(), | 6296 most_general_consolidated_map->elements_kind(), |
6294 map->elements_kind())) { | 6297 map->elements_kind())) { |
6295 most_general_consolidated_map = map; | 6298 most_general_consolidated_map = map; |
6296 } | 6299 } |
6297 } | 6300 } |
6298 if (!has_double_maps && !has_smi_or_object_maps) return NULL; | 6301 if (!has_double_maps && !has_smi_or_object_maps) return NULL; |
6299 | 6302 |
6300 HCheckMaps* checked_object = Add<HCheckMaps>(object, maps); | 6303 HCheckMaps* checked_object = Add<HCheckMaps>(object, maps, top_info()); |
6301 // FAST_ELEMENTS is considered more general than FAST_HOLEY_SMI_ELEMENTS. | 6304 // FAST_ELEMENTS is considered more general than FAST_HOLEY_SMI_ELEMENTS. |
6302 // If we've seen both, the consolidated load must use FAST_HOLEY_ELEMENTS. | 6305 // If we've seen both, the consolidated load must use FAST_HOLEY_ELEMENTS. |
6303 ElementsKind consolidated_elements_kind = has_seen_holey_elements | 6306 ElementsKind consolidated_elements_kind = has_seen_holey_elements |
6304 ? GetHoleyElementsKind(most_general_consolidated_map->elements_kind()) | 6307 ? GetHoleyElementsKind(most_general_consolidated_map->elements_kind()) |
6305 : most_general_consolidated_map->elements_kind(); | 6308 : most_general_consolidated_map->elements_kind(); |
6306 HInstruction* instr = BuildUncheckedMonomorphicElementAccess( | 6309 HInstruction* instr = BuildUncheckedMonomorphicElementAccess( |
6307 checked_object, key, val, | 6310 checked_object, key, val, |
6308 most_general_consolidated_map->instance_type() == JS_ARRAY_TYPE, | 6311 most_general_consolidated_map->instance_type() == JS_ARRAY_TYPE, |
6309 consolidated_elements_kind, | 6312 consolidated_elements_kind, |
6310 LOAD, NEVER_RETURN_HOLE, STANDARD_STORE); | 6313 LOAD, NEVER_RETURN_HOLE, STANDARD_STORE); |
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6388 | 6391 |
6389 HBasicBlock* join = graph()->CreateBasicBlock(); | 6392 HBasicBlock* join = graph()->CreateBasicBlock(); |
6390 | 6393 |
6391 for (int i = 0; i < untransitionable_maps.length(); ++i) { | 6394 for (int i = 0; i < untransitionable_maps.length(); ++i) { |
6392 Handle<Map> map = untransitionable_maps[i]; | 6395 Handle<Map> map = untransitionable_maps[i]; |
6393 if (!map->IsJSObjectMap()) continue; | 6396 if (!map->IsJSObjectMap()) continue; |
6394 ElementsKind elements_kind = map->elements_kind(); | 6397 ElementsKind elements_kind = map->elements_kind(); |
6395 HBasicBlock* this_map = graph()->CreateBasicBlock(); | 6398 HBasicBlock* this_map = graph()->CreateBasicBlock(); |
6396 HBasicBlock* other_map = graph()->CreateBasicBlock(); | 6399 HBasicBlock* other_map = graph()->CreateBasicBlock(); |
6397 HCompareMap* mapcompare = | 6400 HCompareMap* mapcompare = |
6398 New<HCompareMap>(object, map, this_map, other_map); | 6401 New<HCompareMap>(object, map, top_info(), this_map, other_map); |
6399 FinishCurrentBlock(mapcompare); | 6402 FinishCurrentBlock(mapcompare); |
6400 | 6403 |
6401 set_current_block(this_map); | 6404 set_current_block(this_map); |
6402 HInstruction* access = NULL; | 6405 HInstruction* access = NULL; |
6403 if (IsDictionaryElementsKind(elements_kind)) { | 6406 if (IsDictionaryElementsKind(elements_kind)) { |
6404 access = AddInstruction(BuildKeyedGeneric(access_type, object, key, val)); | 6407 access = AddInstruction(BuildKeyedGeneric(access_type, object, key, val)); |
6405 } else { | 6408 } else { |
6406 ASSERT(IsFastElementsKind(elements_kind) || | 6409 ASSERT(IsFastElementsKind(elements_kind) || |
6407 IsExternalArrayElementsKind(elements_kind)); | 6410 IsExternalArrayElementsKind(elements_kind)); |
6408 LoadKeyedHoleMode load_mode = BuildKeyedHoleMode(map); | 6411 LoadKeyedHoleMode load_mode = BuildKeyedHoleMode(map); |
(...skipping 187 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6596 } | 6599 } |
6597 | 6600 |
6598 HValue* checked_object; | 6601 HValue* checked_object; |
6599 // Type::Number() is only supported by polymorphic load/call handling. | 6602 // Type::Number() is only supported by polymorphic load/call handling. |
6600 ASSERT(!info.type()->Is(Type::Number())); | 6603 ASSERT(!info.type()->Is(Type::Number())); |
6601 BuildCheckHeapObject(object); | 6604 BuildCheckHeapObject(object); |
6602 if (AreStringTypes(types)) { | 6605 if (AreStringTypes(types)) { |
6603 checked_object = | 6606 checked_object = |
6604 Add<HCheckInstanceType>(object, HCheckInstanceType::IS_STRING); | 6607 Add<HCheckInstanceType>(object, HCheckInstanceType::IS_STRING); |
6605 } else { | 6608 } else { |
6606 checked_object = Add<HCheckMaps>(object, types); | 6609 checked_object = Add<HCheckMaps>(object, types, top_info()); |
6607 } | 6610 } |
6608 return BuildMonomorphicAccess( | 6611 return BuildMonomorphicAccess( |
6609 &info, object, checked_object, value, ast_id, return_id); | 6612 &info, object, checked_object, value, ast_id, return_id); |
6610 } | 6613 } |
6611 | 6614 |
6612 return BuildNamedGeneric(access, object, name, value, is_uninitialized); | 6615 return BuildNamedGeneric(access, object, name, value, is_uninitialized); |
6613 } | 6616 } |
6614 | 6617 |
6615 | 6618 |
6616 void HOptimizedGraphBuilder::PushLoad(Property* expr, | 6619 void HOptimizedGraphBuilder::PushLoad(Property* expr, |
(...skipping 231 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6848 } | 6851 } |
6849 } | 6852 } |
6850 ++count; | 6853 ++count; |
6851 HBasicBlock* if_true = graph()->CreateBasicBlock(); | 6854 HBasicBlock* if_true = graph()->CreateBasicBlock(); |
6852 HBasicBlock* if_false = graph()->CreateBasicBlock(); | 6855 HBasicBlock* if_false = graph()->CreateBasicBlock(); |
6853 HUnaryControlInstruction* compare; | 6856 HUnaryControlInstruction* compare; |
6854 | 6857 |
6855 Handle<Map> map = info.map(); | 6858 Handle<Map> map = info.map(); |
6856 if (info.type()->Is(Type::Number())) { | 6859 if (info.type()->Is(Type::Number())) { |
6857 Handle<Map> heap_number_map = isolate()->factory()->heap_number_map(); | 6860 Handle<Map> heap_number_map = isolate()->factory()->heap_number_map(); |
6858 compare = New<HCompareMap>(receiver, heap_number_map, if_true, if_false); | 6861 compare = New<HCompareMap>(receiver, heap_number_map, top_info(), |
| 6862 if_true, if_false); |
6859 } else if (info.type()->Is(Type::String())) { | 6863 } else if (info.type()->Is(Type::String())) { |
6860 compare = New<HIsStringAndBranch>(receiver, if_true, if_false); | 6864 compare = New<HIsStringAndBranch>(receiver, if_true, if_false); |
6861 } else { | 6865 } else { |
6862 compare = New<HCompareMap>(receiver, map, if_true, if_false); | 6866 compare = New<HCompareMap>(receiver, map, top_info(), |
| 6867 if_true, if_false); |
6863 } | 6868 } |
6864 FinishCurrentBlock(compare); | 6869 FinishCurrentBlock(compare); |
6865 | 6870 |
6866 if (info.type()->Is(Type::Number())) { | 6871 if (info.type()->Is(Type::Number())) { |
6867 Goto(if_true, number_block); | 6872 Goto(if_true, number_block); |
6868 if_true = number_block; | 6873 if_true = number_block; |
6869 number_block->SetJoinId(expr->id()); | 6874 number_block->SetJoinId(expr->id()); |
6870 } | 6875 } |
6871 | 6876 |
6872 set_current_block(if_true); | 6877 set_current_block(if_true); |
(...skipping 824 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7697 PrintF("Inlining api function "); | 7702 PrintF("Inlining api function "); |
7698 function->ShortPrint(); | 7703 function->ShortPrint(); |
7699 PrintF("\n"); | 7704 PrintF("\n"); |
7700 } | 7705 } |
7701 | 7706 |
7702 bool drop_extra = false; | 7707 bool drop_extra = false; |
7703 switch (call_type) { | 7708 switch (call_type) { |
7704 case kCallApiFunction: | 7709 case kCallApiFunction: |
7705 case kCallApiMethod: | 7710 case kCallApiMethod: |
7706 // Need to check that none of the receiver maps could have changed. | 7711 // Need to check that none of the receiver maps could have changed. |
7707 Add<HCheckMaps>(receiver, receiver_maps); | 7712 Add<HCheckMaps>(receiver, receiver_maps, top_info()); |
7708 // Need to ensure the chain between receiver and api_holder is intact. | 7713 // Need to ensure the chain between receiver and api_holder is intact. |
7709 if (holder_lookup == CallOptimization::kHolderFound) { | 7714 if (holder_lookup == CallOptimization::kHolderFound) { |
7710 AddCheckPrototypeMaps(api_holder, receiver_maps->first()); | 7715 AddCheckPrototypeMaps(api_holder, receiver_maps->first()); |
7711 } else { | 7716 } else { |
7712 ASSERT_EQ(holder_lookup, CallOptimization::kHolderIsReceiver); | 7717 ASSERT_EQ(holder_lookup, CallOptimization::kHolderIsReceiver); |
7713 } | 7718 } |
7714 // Includes receiver. | 7719 // Includes receiver. |
7715 PushArgumentsFromEnvironment(argc + 1); | 7720 PushArgumentsFromEnvironment(argc + 1); |
7716 // Drop function after call. | 7721 // Drop function after call. |
7717 drop_extra = true; | 7722 drop_extra = true; |
(...skipping 3464 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
11182 if (ShouldProduceTraceOutput()) { | 11187 if (ShouldProduceTraceOutput()) { |
11183 isolate()->GetHTracer()->TraceHydrogen(name(), graph_); | 11188 isolate()->GetHTracer()->TraceHydrogen(name(), graph_); |
11184 } | 11189 } |
11185 | 11190 |
11186 #ifdef DEBUG | 11191 #ifdef DEBUG |
11187 graph_->Verify(false); // No full verify. | 11192 graph_->Verify(false); // No full verify. |
11188 #endif | 11193 #endif |
11189 } | 11194 } |
11190 | 11195 |
11191 } } // namespace v8::internal | 11196 } } // namespace v8::internal |
OLD | NEW |