OLD | NEW |
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 #include "src/code-stubs.h" | 5 #include "src/code-stubs.h" |
6 | 6 |
7 #include <sstream> | 7 #include <sstream> |
8 | 8 |
9 #include "src/ast/ast.h" | 9 #include "src/ast/ast.h" |
10 #include "src/bootstrapper.h" | 10 #include "src/bootstrapper.h" |
(...skipping 713 matching lines...) Loading... |
724 } | 724 } |
725 | 725 |
726 assembler->Bind(&if_rhsisnotsmi); | 726 assembler->Bind(&if_rhsisnotsmi); |
727 { | 727 { |
728 // Load the map of {rhs}. | 728 // Load the map of {rhs}. |
729 Node* rhs_map = assembler->LoadMap(rhs); | 729 Node* rhs_map = assembler->LoadMap(rhs); |
730 | 730 |
731 // Check if the {rhs} is a HeapNumber. | 731 // Check if the {rhs} is a HeapNumber. |
732 Label if_rhsisnumber(assembler), | 732 Label if_rhsisnumber(assembler), |
733 if_rhsisnotnumber(assembler, Label::kDeferred); | 733 if_rhsisnotnumber(assembler, Label::kDeferred); |
734 Node* number_map = assembler->HeapNumberMapConstant(); | 734 assembler->Branch(assembler->IsHeapNumberMap(rhs_map), &if_rhsisnumber, |
735 assembler->Branch(assembler->WordEqual(rhs_map, number_map), | 735 &if_rhsisnotnumber); |
736 &if_rhsisnumber, &if_rhsisnotnumber); | |
737 | 736 |
738 assembler->Bind(&if_rhsisnumber); | 737 assembler->Bind(&if_rhsisnumber); |
739 { | 738 { |
740 var_fadd_lhs.Bind(assembler->SmiToFloat64(lhs)); | 739 var_fadd_lhs.Bind(assembler->SmiToFloat64(lhs)); |
741 var_fadd_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); | 740 var_fadd_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); |
742 assembler->Goto(&do_fadd); | 741 assembler->Goto(&do_fadd); |
743 } | 742 } |
744 | 743 |
745 assembler->Bind(&if_rhsisnotnumber); | 744 assembler->Bind(&if_rhsisnotnumber); |
746 { | 745 { |
(...skipping 343 matching lines...) Loading... |
1090 assembler->Goto(&end); | 1089 assembler->Goto(&end); |
1091 } | 1090 } |
1092 } | 1091 } |
1093 | 1092 |
1094 assembler->Bind(&if_rhsisnotsmi); | 1093 assembler->Bind(&if_rhsisnotsmi); |
1095 { | 1094 { |
1096 // Load the map of {rhs}. | 1095 // Load the map of {rhs}. |
1097 Node* rhs_map = assembler->LoadMap(rhs); | 1096 Node* rhs_map = assembler->LoadMap(rhs); |
1098 | 1097 |
1099 // Check if the {rhs} is a HeapNumber. | 1098 // Check if the {rhs} is a HeapNumber. |
1100 assembler->GotoUnless( | 1099 assembler->GotoUnless(assembler->IsHeapNumberMap(rhs_map), |
1101 assembler->WordEqual(rhs_map, assembler->HeapNumberMapConstant()), | 1100 &call_add_stub); |
1102 &call_add_stub); | |
1103 | 1101 |
1104 var_fadd_lhs.Bind(assembler->SmiToFloat64(lhs)); | 1102 var_fadd_lhs.Bind(assembler->SmiToFloat64(lhs)); |
1105 var_fadd_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); | 1103 var_fadd_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); |
1106 assembler->Goto(&do_fadd); | 1104 assembler->Goto(&do_fadd); |
1107 } | 1105 } |
1108 } | 1106 } |
1109 | 1107 |
1110 assembler->Bind(&if_lhsisnotsmi); | 1108 assembler->Bind(&if_lhsisnotsmi); |
1111 { | 1109 { |
1112 // Load the map of {lhs}. | 1110 // Load the map of {lhs}. |
1113 Node* lhs_map = assembler->LoadMap(lhs); | 1111 Node* lhs_map = assembler->LoadMap(lhs); |
1114 | 1112 |
1115 // Check if {lhs} is a HeapNumber. | 1113 // Check if {lhs} is a HeapNumber. |
1116 Label if_lhsisnumber(assembler), if_lhsisnotnumber(assembler); | 1114 Label if_lhsisnumber(assembler), if_lhsisnotnumber(assembler); |
1117 assembler->GotoUnless( | 1115 assembler->GotoUnless(assembler->IsHeapNumberMap(lhs_map), &call_add_stub); |
1118 assembler->WordEqual(lhs_map, assembler->HeapNumberMapConstant()), | |
1119 &call_add_stub); | |
1120 | 1116 |
1121 // Check if the {rhs} is Smi. | 1117 // Check if the {rhs} is Smi. |
1122 Label if_rhsissmi(assembler), if_rhsisnotsmi(assembler); | 1118 Label if_rhsissmi(assembler), if_rhsisnotsmi(assembler); |
1123 assembler->Branch(assembler->WordIsSmi(rhs), &if_rhsissmi, &if_rhsisnotsmi); | 1119 assembler->Branch(assembler->WordIsSmi(rhs), &if_rhsissmi, &if_rhsisnotsmi); |
1124 | 1120 |
1125 assembler->Bind(&if_rhsissmi); | 1121 assembler->Bind(&if_rhsissmi); |
1126 { | 1122 { |
1127 var_fadd_lhs.Bind(assembler->LoadHeapNumberValue(lhs)); | 1123 var_fadd_lhs.Bind(assembler->LoadHeapNumberValue(lhs)); |
1128 var_fadd_rhs.Bind(assembler->SmiToFloat64(rhs)); | 1124 var_fadd_rhs.Bind(assembler->SmiToFloat64(rhs)); |
1129 assembler->Goto(&do_fadd); | 1125 assembler->Goto(&do_fadd); |
1130 } | 1126 } |
1131 | 1127 |
1132 assembler->Bind(&if_rhsisnotsmi); | 1128 assembler->Bind(&if_rhsisnotsmi); |
1133 { | 1129 { |
1134 // Load the map of {rhs}. | 1130 // Load the map of {rhs}. |
1135 Node* rhs_map = assembler->LoadMap(rhs); | 1131 Node* rhs_map = assembler->LoadMap(rhs); |
1136 | 1132 |
1137 // Check if the {rhs} is a HeapNumber. | 1133 // Check if the {rhs} is a HeapNumber. |
1138 Node* number_map = assembler->HeapNumberMapConstant(); | 1134 assembler->GotoUnless(assembler->IsHeapNumberMap(rhs_map), |
1139 assembler->GotoUnless(assembler->WordEqual(rhs_map, number_map), | |
1140 &call_add_stub); | 1135 &call_add_stub); |
1141 | 1136 |
1142 var_fadd_lhs.Bind(assembler->LoadHeapNumberValue(lhs)); | 1137 var_fadd_lhs.Bind(assembler->LoadHeapNumberValue(lhs)); |
1143 var_fadd_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); | 1138 var_fadd_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); |
1144 assembler->Goto(&do_fadd); | 1139 assembler->Goto(&do_fadd); |
1145 } | 1140 } |
1146 } | 1141 } |
1147 | 1142 |
1148 assembler->Bind(&do_fadd); | 1143 assembler->Bind(&do_fadd); |
1149 { | 1144 { |
(...skipping 86 matching lines...) Loading... |
1236 } | 1231 } |
1237 | 1232 |
1238 assembler->Bind(&if_rhsisnotsmi); | 1233 assembler->Bind(&if_rhsisnotsmi); |
1239 { | 1234 { |
1240 // Load the map of the {rhs}. | 1235 // Load the map of the {rhs}. |
1241 Node* rhs_map = assembler->LoadMap(rhs); | 1236 Node* rhs_map = assembler->LoadMap(rhs); |
1242 | 1237 |
1243 // Check if {rhs} is a HeapNumber. | 1238 // Check if {rhs} is a HeapNumber. |
1244 Label if_rhsisnumber(assembler), | 1239 Label if_rhsisnumber(assembler), |
1245 if_rhsisnotnumber(assembler, Label::kDeferred); | 1240 if_rhsisnotnumber(assembler, Label::kDeferred); |
1246 Node* number_map = assembler->HeapNumberMapConstant(); | 1241 assembler->Branch(assembler->IsHeapNumberMap(rhs_map), &if_rhsisnumber, |
1247 assembler->Branch(assembler->WordEqual(rhs_map, number_map), | 1242 &if_rhsisnotnumber); |
1248 &if_rhsisnumber, &if_rhsisnotnumber); | |
1249 | 1243 |
1250 assembler->Bind(&if_rhsisnumber); | 1244 assembler->Bind(&if_rhsisnumber); |
1251 { | 1245 { |
1252 // Perform a floating point subtraction. | 1246 // Perform a floating point subtraction. |
1253 var_fsub_lhs.Bind(assembler->SmiToFloat64(lhs)); | 1247 var_fsub_lhs.Bind(assembler->SmiToFloat64(lhs)); |
1254 var_fsub_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); | 1248 var_fsub_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); |
1255 assembler->Goto(&do_fsub); | 1249 assembler->Goto(&do_fsub); |
1256 } | 1250 } |
1257 | 1251 |
1258 assembler->Bind(&if_rhsisnotnumber); | 1252 assembler->Bind(&if_rhsisnotnumber); |
(...skipping 140 matching lines...) Loading... |
1399 var_result.Bind(assembler->Projection(0, pair)); | 1393 var_result.Bind(assembler->Projection(0, pair)); |
1400 assembler->Goto(&end); | 1394 assembler->Goto(&end); |
1401 } | 1395 } |
1402 | 1396 |
1403 assembler->Bind(&if_rhsisnotsmi); | 1397 assembler->Bind(&if_rhsisnotsmi); |
1404 { | 1398 { |
1405 // Load the map of the {rhs}. | 1399 // Load the map of the {rhs}. |
1406 Node* rhs_map = assembler->LoadMap(rhs); | 1400 Node* rhs_map = assembler->LoadMap(rhs); |
1407 | 1401 |
1408 // Check if {rhs} is a HeapNumber. | 1402 // Check if {rhs} is a HeapNumber. |
1409 assembler->GotoUnless( | 1403 assembler->GotoUnless(assembler->IsHeapNumberMap(rhs_map), |
1410 assembler->WordEqual(rhs_map, assembler->HeapNumberMapConstant()), | 1404 &call_subtract_stub); |
1411 &call_subtract_stub); | |
1412 | 1405 |
1413 // Perform a floating point subtraction. | 1406 // Perform a floating point subtraction. |
1414 var_fsub_lhs.Bind(assembler->SmiToFloat64(lhs)); | 1407 var_fsub_lhs.Bind(assembler->SmiToFloat64(lhs)); |
1415 var_fsub_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); | 1408 var_fsub_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); |
1416 assembler->Goto(&do_fsub); | 1409 assembler->Goto(&do_fsub); |
1417 } | 1410 } |
1418 } | 1411 } |
1419 | 1412 |
1420 assembler->Bind(&if_lhsisnotsmi); | 1413 assembler->Bind(&if_lhsisnotsmi); |
1421 { | 1414 { |
1422 // Load the map of the {lhs}. | 1415 // Load the map of the {lhs}. |
1423 Node* lhs_map = assembler->LoadMap(lhs); | 1416 Node* lhs_map = assembler->LoadMap(lhs); |
1424 | 1417 |
1425 // Check if the {lhs} is a HeapNumber. | 1418 // Check if the {lhs} is a HeapNumber. |
1426 assembler->GotoUnless( | 1419 assembler->GotoUnless(assembler->IsHeapNumberMap(lhs_map), |
1427 assembler->WordEqual(lhs_map, assembler->HeapNumberMapConstant()), | 1420 &call_subtract_stub); |
1428 &call_subtract_stub); | |
1429 | 1421 |
1430 // Check if the {rhs} is a Smi. | 1422 // Check if the {rhs} is a Smi. |
1431 Label if_rhsissmi(assembler), if_rhsisnotsmi(assembler); | 1423 Label if_rhsissmi(assembler), if_rhsisnotsmi(assembler); |
1432 assembler->Branch(assembler->WordIsSmi(rhs), &if_rhsissmi, &if_rhsisnotsmi); | 1424 assembler->Branch(assembler->WordIsSmi(rhs), &if_rhsissmi, &if_rhsisnotsmi); |
1433 | 1425 |
1434 assembler->Bind(&if_rhsissmi); | 1426 assembler->Bind(&if_rhsissmi); |
1435 { | 1427 { |
1436 // Perform a floating point subtraction. | 1428 // Perform a floating point subtraction. |
1437 var_fsub_lhs.Bind(assembler->LoadHeapNumberValue(lhs)); | 1429 var_fsub_lhs.Bind(assembler->LoadHeapNumberValue(lhs)); |
1438 var_fsub_rhs.Bind(assembler->SmiToFloat64(rhs)); | 1430 var_fsub_rhs.Bind(assembler->SmiToFloat64(rhs)); |
1439 assembler->Goto(&do_fsub); | 1431 assembler->Goto(&do_fsub); |
1440 } | 1432 } |
1441 | 1433 |
1442 assembler->Bind(&if_rhsisnotsmi); | 1434 assembler->Bind(&if_rhsisnotsmi); |
1443 { | 1435 { |
1444 // Load the map of the {rhs}. | 1436 // Load the map of the {rhs}. |
1445 Node* rhs_map = assembler->LoadMap(rhs); | 1437 Node* rhs_map = assembler->LoadMap(rhs); |
1446 | 1438 |
1447 // Check if the {rhs} is a HeapNumber. | 1439 // Check if the {rhs} is a HeapNumber. |
1448 assembler->GotoUnless( | 1440 assembler->GotoUnless(assembler->IsHeapNumberMap(rhs_map), |
1449 assembler->WordEqual(rhs_map, assembler->HeapNumberMapConstant()), | 1441 &call_subtract_stub); |
1450 &call_subtract_stub); | |
1451 | 1442 |
1452 // Perform a floating point subtraction. | 1443 // Perform a floating point subtraction. |
1453 var_fsub_lhs.Bind(assembler->LoadHeapNumberValue(lhs)); | 1444 var_fsub_lhs.Bind(assembler->LoadHeapNumberValue(lhs)); |
1454 var_fsub_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); | 1445 var_fsub_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); |
1455 assembler->Goto(&do_fsub); | 1446 assembler->Goto(&do_fsub); |
1456 } | 1447 } |
1457 } | 1448 } |
1458 | 1449 |
1459 assembler->Bind(&do_fsub); | 1450 assembler->Bind(&do_fsub); |
1460 { | 1451 { |
(...skipping 1105 matching lines...) Loading... |
2566 assembler->Goto(&do_finc); | 2557 assembler->Goto(&do_finc); |
2567 } | 2558 } |
2568 } | 2559 } |
2569 | 2560 |
2570 assembler->Bind(&if_isnotsmi); | 2561 assembler->Bind(&if_isnotsmi); |
2571 { | 2562 { |
2572 // Check if the value is a HeapNumber. | 2563 // Check if the value is a HeapNumber. |
2573 Label if_valueisnumber(assembler), | 2564 Label if_valueisnumber(assembler), |
2574 if_valuenotnumber(assembler, Label::kDeferred); | 2565 if_valuenotnumber(assembler, Label::kDeferred); |
2575 Node* value_map = assembler->LoadMap(value); | 2566 Node* value_map = assembler->LoadMap(value); |
2576 Node* number_map = assembler->HeapNumberMapConstant(); | 2567 assembler->Branch(assembler->IsHeapNumberMap(value_map), |
2577 assembler->Branch(assembler->WordEqual(value_map, number_map), | |
2578 &if_valueisnumber, &if_valuenotnumber); | 2568 &if_valueisnumber, &if_valuenotnumber); |
2579 | 2569 |
2580 assembler->Bind(&if_valueisnumber); | 2570 assembler->Bind(&if_valueisnumber); |
2581 { | 2571 { |
2582 // Load the HeapNumber value. | 2572 // Load the HeapNumber value. |
2583 var_finc_value.Bind(assembler->LoadHeapNumberValue(value)); | 2573 var_finc_value.Bind(assembler->LoadHeapNumberValue(value)); |
2584 assembler->Goto(&do_finc); | 2574 assembler->Goto(&do_finc); |
2585 } | 2575 } |
2586 | 2576 |
2587 assembler->Bind(&if_valuenotnumber); | 2577 assembler->Bind(&if_valuenotnumber); |
(...skipping 82 matching lines...) Loading... |
2670 assembler->Goto(&do_fdec); | 2660 assembler->Goto(&do_fdec); |
2671 } | 2661 } |
2672 } | 2662 } |
2673 | 2663 |
2674 assembler->Bind(&if_isnotsmi); | 2664 assembler->Bind(&if_isnotsmi); |
2675 { | 2665 { |
2676 // Check if the value is a HeapNumber. | 2666 // Check if the value is a HeapNumber. |
2677 Label if_valueisnumber(assembler), | 2667 Label if_valueisnumber(assembler), |
2678 if_valuenotnumber(assembler, Label::kDeferred); | 2668 if_valuenotnumber(assembler, Label::kDeferred); |
2679 Node* value_map = assembler->LoadMap(value); | 2669 Node* value_map = assembler->LoadMap(value); |
2680 Node* number_map = assembler->HeapNumberMapConstant(); | 2670 assembler->Branch(assembler->IsHeapNumberMap(value_map), |
2681 assembler->Branch(assembler->WordEqual(value_map, number_map), | |
2682 &if_valueisnumber, &if_valuenotnumber); | 2671 &if_valueisnumber, &if_valuenotnumber); |
2683 | 2672 |
2684 assembler->Bind(&if_valueisnumber); | 2673 assembler->Bind(&if_valueisnumber); |
2685 { | 2674 { |
2686 // Load the HeapNumber value. | 2675 // Load the HeapNumber value. |
2687 var_fdec_value.Bind(assembler->LoadHeapNumberValue(value)); | 2676 var_fdec_value.Bind(assembler->LoadHeapNumberValue(value)); |
2688 assembler->Goto(&do_fdec); | 2677 assembler->Goto(&do_fdec); |
2689 } | 2678 } |
2690 | 2679 |
2691 assembler->Bind(&if_valuenotnumber); | 2680 assembler->Bind(&if_valuenotnumber); |
(...skipping 50 matching lines...) Loading... |
2742 Node* context = assembler->Parameter(Descriptor::kContext); | 2731 Node* context = assembler->Parameter(Descriptor::kContext); |
2743 | 2732 |
2744 Variable constructor_function_index_var(assembler, | 2733 Variable constructor_function_index_var(assembler, |
2745 MachineType::PointerRepresentation()); | 2734 MachineType::PointerRepresentation()); |
2746 | 2735 |
2747 assembler->Branch(assembler->WordIsSmi(object), &if_number, &if_notsmi); | 2736 assembler->Branch(assembler->WordIsSmi(object), &if_number, &if_notsmi); |
2748 | 2737 |
2749 assembler->Bind(&if_notsmi); | 2738 assembler->Bind(&if_notsmi); |
2750 Node* map = assembler->LoadMap(object); | 2739 Node* map = assembler->LoadMap(object); |
2751 | 2740 |
2752 assembler->GotoIf( | 2741 assembler->GotoIf(assembler->IsHeapNumberMap(map), &if_number); |
2753 assembler->WordEqual(map, assembler->HeapNumberMapConstant()), | |
2754 &if_number); | |
2755 | 2742 |
2756 Node* instance_type = assembler->LoadMapInstanceType(map); | 2743 Node* instance_type = assembler->LoadMapInstanceType(map); |
2757 assembler->GotoIf( | 2744 assembler->GotoIf( |
2758 assembler->Int32GreaterThanOrEqual( | 2745 assembler->Int32GreaterThanOrEqual( |
2759 instance_type, assembler->Int32Constant(FIRST_JS_RECEIVER_TYPE)), | 2746 instance_type, assembler->Int32Constant(FIRST_JS_RECEIVER_TYPE)), |
2760 &if_jsreceiver); | 2747 &if_jsreceiver); |
2761 | 2748 |
2762 Node* constructor_function_index = | 2749 Node* constructor_function_index = |
2763 assembler->LoadMapConstructorFunctionIndex(map); | 2750 assembler->LoadMapConstructorFunctionIndex(map); |
2764 assembler->GotoIf(assembler->WordEqual(constructor_function_index, | 2751 assembler->GotoIf(assembler->WordEqual(constructor_function_index, |
(...skipping 47 matching lines...) Loading... |
2812 | 2799 |
2813 Label return_number(assembler, Label::kDeferred), if_oddball(assembler), | 2800 Label return_number(assembler, Label::kDeferred), if_oddball(assembler), |
2814 return_function(assembler), return_undefined(assembler), | 2801 return_function(assembler), return_undefined(assembler), |
2815 return_object(assembler), return_string(assembler), | 2802 return_object(assembler), return_string(assembler), |
2816 return_result(assembler); | 2803 return_result(assembler); |
2817 | 2804 |
2818 assembler->GotoIf(assembler->WordIsSmi(value), &return_number); | 2805 assembler->GotoIf(assembler->WordIsSmi(value), &return_number); |
2819 | 2806 |
2820 Node* map = assembler->LoadMap(value); | 2807 Node* map = assembler->LoadMap(value); |
2821 | 2808 |
2822 assembler->GotoIf( | 2809 assembler->GotoIf(assembler->IsHeapNumberMap(map), &return_number); |
2823 assembler->WordEqual(map, assembler->HeapNumberMapConstant()), | |
2824 &return_number); | |
2825 | 2810 |
2826 Node* instance_type = assembler->LoadMapInstanceType(map); | 2811 Node* instance_type = assembler->LoadMapInstanceType(map); |
2827 | 2812 |
2828 assembler->GotoIf(assembler->Word32Equal( | 2813 assembler->GotoIf(assembler->Word32Equal( |
2829 instance_type, assembler->Int32Constant(ODDBALL_TYPE)), | 2814 instance_type, assembler->Int32Constant(ODDBALL_TYPE)), |
2830 &if_oddball); | 2815 &if_oddball); |
2831 | 2816 |
2832 Node* callable_or_undetectable_mask = | 2817 Node* callable_or_undetectable_mask = |
2833 assembler->Word32And(assembler->LoadMapBitField(map), | 2818 assembler->Word32And(assembler->LoadMapBitField(map), |
2834 assembler->Int32Constant(1 << Map::kIsCallable | | 2819 assembler->Int32Constant(1 << Map::kIsCallable | |
(...skipping 206 matching lines...) Loading... |
3041 break; | 3026 break; |
3042 } | 3027 } |
3043 } | 3028 } |
3044 | 3029 |
3045 assembler->Bind(&if_rhsisnotsmi); | 3030 assembler->Bind(&if_rhsisnotsmi); |
3046 { | 3031 { |
3047 // Load the map of {rhs}. | 3032 // Load the map of {rhs}. |
3048 Node* rhs_map = assembler->LoadMap(rhs); | 3033 Node* rhs_map = assembler->LoadMap(rhs); |
3049 | 3034 |
3050 // Check if the {rhs} is a HeapNumber. | 3035 // Check if the {rhs} is a HeapNumber. |
3051 Node* number_map = assembler->HeapNumberMapConstant(); | |
3052 Label if_rhsisnumber(assembler), | 3036 Label if_rhsisnumber(assembler), |
3053 if_rhsisnotnumber(assembler, Label::kDeferred); | 3037 if_rhsisnotnumber(assembler, Label::kDeferred); |
3054 assembler->Branch(assembler->WordEqual(rhs_map, number_map), | 3038 assembler->Branch(assembler->IsHeapNumberMap(rhs_map), &if_rhsisnumber, |
3055 &if_rhsisnumber, &if_rhsisnotnumber); | 3039 &if_rhsisnotnumber); |
3056 | 3040 |
3057 assembler->Bind(&if_rhsisnumber); | 3041 assembler->Bind(&if_rhsisnumber); |
3058 { | 3042 { |
3059 // Convert the {lhs} and {rhs} to floating point values, and | 3043 // Convert the {lhs} and {rhs} to floating point values, and |
3060 // perform a floating point comparison. | 3044 // perform a floating point comparison. |
3061 var_fcmp_lhs.Bind(assembler->SmiToFloat64(lhs)); | 3045 var_fcmp_lhs.Bind(assembler->SmiToFloat64(lhs)); |
3062 var_fcmp_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); | 3046 var_fcmp_rhs.Bind(assembler->LoadHeapNumberValue(rhs)); |
3063 assembler->Goto(&do_fcmp); | 3047 assembler->Goto(&do_fcmp); |
3064 } | 3048 } |
3065 | 3049 |
(...skipping 285 matching lines...) Loading... |
3351 Label if_valueissmi(assembler), if_valueisnotsmi(assembler); | 3335 Label if_valueissmi(assembler), if_valueisnotsmi(assembler); |
3352 assembler->Branch(assembler->WordIsSmi(value), &if_valueissmi, | 3336 assembler->Branch(assembler->WordIsSmi(value), &if_valueissmi, |
3353 &if_valueisnotsmi); | 3337 &if_valueisnotsmi); |
3354 | 3338 |
3355 assembler->Bind(&if_valueisnotsmi); | 3339 assembler->Bind(&if_valueisnotsmi); |
3356 { | 3340 { |
3357 // Load the map of {value}. | 3341 // Load the map of {value}. |
3358 Node* value_map = assembler->LoadMap(value); | 3342 Node* value_map = assembler->LoadMap(value); |
3359 | 3343 |
3360 // Check if {value} (and therefore {rhs}) is a HeapNumber. | 3344 // Check if {value} (and therefore {rhs}) is a HeapNumber. |
3361 Node* number_map = assembler->HeapNumberMapConstant(); | |
3362 Label if_valueisnumber(assembler), if_valueisnotnumber(assembler); | 3345 Label if_valueisnumber(assembler), if_valueisnotnumber(assembler); |
3363 assembler->Branch(assembler->WordEqual(value_map, number_map), | 3346 assembler->Branch(assembler->IsHeapNumberMap(value_map), &if_valueisnumber, |
3364 &if_valueisnumber, &if_valueisnotnumber); | 3347 &if_valueisnotnumber); |
3365 | 3348 |
3366 assembler->Bind(&if_valueisnumber); | 3349 assembler->Bind(&if_valueisnumber); |
3367 { | 3350 { |
3368 // Convert {value} (and therefore {rhs}) to floating point value. | 3351 // Convert {value} (and therefore {rhs}) to floating point value. |
3369 Node* value_value = assembler->LoadHeapNumberValue(value); | 3352 Node* value_value = assembler->LoadHeapNumberValue(value); |
3370 | 3353 |
3371 // Check if the HeapNumber value is a NaN. | 3354 // Check if the HeapNumber value is a NaN. |
3372 assembler->BranchIfFloat64IsNaN(value_value, if_notequal, if_equal); | 3355 assembler->BranchIfFloat64IsNaN(value_value, if_notequal, if_equal); |
3373 } | 3356 } |
3374 | 3357 |
(...skipping 116 matching lines...) Loading... |
3491 { | 3474 { |
3492 // The {rhs} is a String and the {lhs} is a Smi; we need | 3475 // The {rhs} is a String and the {lhs} is a Smi; we need |
3493 // to convert the {rhs} to a Number and compare the output to | 3476 // to convert the {rhs} to a Number and compare the output to |
3494 // the Number on the {lhs}. | 3477 // the Number on the {lhs}. |
3495 assembler->Goto(&do_rhsstringtonumber); | 3478 assembler->Goto(&do_rhsstringtonumber); |
3496 } | 3479 } |
3497 | 3480 |
3498 assembler->Bind(&if_rhsisnotstring); | 3481 assembler->Bind(&if_rhsisnotstring); |
3499 { | 3482 { |
3500 // Check if the {rhs} is a Boolean. | 3483 // Check if the {rhs} is a Boolean. |
3501 Node* boolean_map = assembler->BooleanMapConstant(); | |
3502 Label if_rhsisboolean(assembler), if_rhsisnotboolean(assembler); | 3484 Label if_rhsisboolean(assembler), if_rhsisnotboolean(assembler); |
3503 assembler->Branch(assembler->WordEqual(rhs_map, boolean_map), | 3485 assembler->Branch(assembler->IsBooleanMap(rhs_map), |
3504 &if_rhsisboolean, &if_rhsisnotboolean); | 3486 &if_rhsisboolean, &if_rhsisnotboolean); |
3505 | 3487 |
3506 assembler->Bind(&if_rhsisboolean); | 3488 assembler->Bind(&if_rhsisboolean); |
3507 { | 3489 { |
3508 // The {rhs} is a Boolean, load its number value. | 3490 // The {rhs} is a Boolean, load its number value. |
3509 var_rhs.Bind( | 3491 var_rhs.Bind( |
3510 assembler->LoadObjectField(rhs, Oddball::kToNumberOffset)); | 3492 assembler->LoadObjectField(rhs, Oddball::kToNumberOffset)); |
3511 assembler->Goto(&loop); | 3493 assembler->Goto(&loop); |
3512 } | 3494 } |
3513 | 3495 |
(...skipping 175 matching lines...) Loading... |
3689 var_lhs.Bind(rhs); | 3671 var_lhs.Bind(rhs); |
3690 var_rhs.Bind(lhs); | 3672 var_rhs.Bind(lhs); |
3691 assembler->Goto(&loop); | 3673 assembler->Goto(&loop); |
3692 } | 3674 } |
3693 | 3675 |
3694 assembler->Bind(&if_rhsisnotreceiver); | 3676 assembler->Bind(&if_rhsisnotreceiver); |
3695 { | 3677 { |
3696 // Check if {rhs} is a Boolean. | 3678 // Check if {rhs} is a Boolean. |
3697 Label if_rhsisboolean(assembler), | 3679 Label if_rhsisboolean(assembler), |
3698 if_rhsisnotboolean(assembler); | 3680 if_rhsisnotboolean(assembler); |
3699 Node* boolean_map = assembler->BooleanMapConstant(); | 3681 assembler->Branch(assembler->IsBooleanMap(rhs_map), |
3700 assembler->Branch(assembler->WordEqual(rhs_map, boolean_map), | |
3701 &if_rhsisboolean, &if_rhsisnotboolean); | 3682 &if_rhsisboolean, &if_rhsisnotboolean); |
3702 | 3683 |
3703 assembler->Bind(&if_rhsisboolean); | 3684 assembler->Bind(&if_rhsisboolean); |
3704 { | 3685 { |
3705 // The {rhs} is a Boolean, convert it to a Smi first. | 3686 // The {rhs} is a Boolean, convert it to a Smi first. |
3706 var_rhs.Bind(assembler->LoadObjectField( | 3687 var_rhs.Bind(assembler->LoadObjectField( |
3707 rhs, Oddball::kToNumberOffset)); | 3688 rhs, Oddball::kToNumberOffset)); |
3708 assembler->Goto(&loop); | 3689 assembler->Goto(&loop); |
3709 } | 3690 } |
3710 | 3691 |
(...skipping 584 matching lines...) Loading... |
4295 // runtime. | 4276 // runtime. |
4296 Node* cell_contents = | 4277 Node* cell_contents = |
4297 assembler->LoadObjectField(cell, PropertyCell::kValueOffset); | 4278 assembler->LoadObjectField(cell, PropertyCell::kValueOffset); |
4298 | 4279 |
4299 PropertyCellType cell_type = this->cell_type(); | 4280 PropertyCellType cell_type = this->cell_type(); |
4300 if (cell_type == PropertyCellType::kConstant || | 4281 if (cell_type == PropertyCellType::kConstant || |
4301 cell_type == PropertyCellType::kUndefined) { | 4282 cell_type == PropertyCellType::kUndefined) { |
4302 // This is always valid for all states a cell can be in. | 4283 // This is always valid for all states a cell can be in. |
4303 assembler->GotoIf(assembler->WordNotEqual(cell_contents, value), &miss); | 4284 assembler->GotoIf(assembler->WordNotEqual(cell_contents, value), &miss); |
4304 } else { | 4285 } else { |
4305 assembler->GotoIf( | 4286 assembler->GotoIf(assembler->IsTheHole(cell_contents), &miss); |
4306 assembler->WordEqual(cell_contents, assembler->TheHoleConstant()), | |
4307 &miss); | |
4308 | 4287 |
4309 // When dealing with constant types, the type may be allowed to change, as | 4288 // When dealing with constant types, the type may be allowed to change, as |
4310 // long as optimized code remains valid. | 4289 // long as optimized code remains valid. |
4311 bool value_is_smi = false; | 4290 bool value_is_smi = false; |
4312 if (cell_type == PropertyCellType::kConstantType) { | 4291 if (cell_type == PropertyCellType::kConstantType) { |
4313 switch (constant_type()) { | 4292 switch (constant_type()) { |
4314 case PropertyCellConstantType::kSmi: | 4293 case PropertyCellConstantType::kSmi: |
4315 assembler->GotoUnless(assembler->WordIsSmi(value), &miss); | 4294 assembler->GotoUnless(assembler->WordIsSmi(value), &miss); |
4316 value_is_smi = true; | 4295 value_is_smi = true; |
4317 break; | 4296 break; |
(...skipping 201 matching lines...) Loading... |
4519 | 4498 |
4520 // Check if {len} is a positive Smi. | 4499 // Check if {len} is a positive Smi. |
4521 assembler->GotoIf(assembler->WordIsPositiveSmi(len), &return_len); | 4500 assembler->GotoIf(assembler->WordIsPositiveSmi(len), &return_len); |
4522 | 4501 |
4523 // Check if {len} is a (negative) Smi. | 4502 // Check if {len} is a (negative) Smi. |
4524 assembler->GotoIf(assembler->WordIsSmi(len), &return_zero); | 4503 assembler->GotoIf(assembler->WordIsSmi(len), &return_zero); |
4525 | 4504 |
4526 // Check if {len} is a HeapNumber. | 4505 // Check if {len} is a HeapNumber. |
4527 Label if_lenisheapnumber(assembler), | 4506 Label if_lenisheapnumber(assembler), |
4528 if_lenisnotheapnumber(assembler, Label::kDeferred); | 4507 if_lenisnotheapnumber(assembler, Label::kDeferred); |
4529 assembler->Branch(assembler->WordEqual(assembler->LoadMap(len), | 4508 assembler->Branch(assembler->IsHeapNumberMap(assembler->LoadMap(len)), |
4530 assembler->HeapNumberMapConstant()), | |
4531 &if_lenisheapnumber, &if_lenisnotheapnumber); | 4509 &if_lenisheapnumber, &if_lenisnotheapnumber); |
4532 | 4510 |
4533 assembler->Bind(&if_lenisheapnumber); | 4511 assembler->Bind(&if_lenisheapnumber); |
4534 { | 4512 { |
4535 // Load the floating-point value of {len}. | 4513 // Load the floating-point value of {len}. |
4536 Node* len_value = assembler->LoadHeapNumberValue(len); | 4514 Node* len_value = assembler->LoadHeapNumberValue(len); |
4537 | 4515 |
4538 // Check if {len} is not greater than zero. | 4516 // Check if {len} is not greater than zero. |
4539 assembler->GotoUnless(assembler->Float64GreaterThan( | 4517 assembler->GotoUnless(assembler->Float64GreaterThan( |
4540 len_value, assembler->Float64Constant(0.0)), | 4518 len_value, assembler->Float64Constant(0.0)), |
(...skipping 102 matching lines...) Loading... |
4643 typedef compiler::Node Node; | 4621 typedef compiler::Node Node; |
4644 typedef compiler::CodeAssembler::Label Label; | 4622 typedef compiler::CodeAssembler::Label Label; |
4645 typedef compiler::CodeAssembler::Variable Variable; | 4623 typedef compiler::CodeAssembler::Variable Variable; |
4646 | 4624 |
4647 Node* literals_array = | 4625 Node* literals_array = |
4648 assembler->LoadObjectField(closure, JSFunction::kLiteralsOffset); | 4626 assembler->LoadObjectField(closure, JSFunction::kLiteralsOffset); |
4649 Node* allocation_site = assembler->LoadFixedArrayElement( | 4627 Node* allocation_site = assembler->LoadFixedArrayElement( |
4650 literals_array, literals_index, | 4628 literals_array, literals_index, |
4651 LiteralsArray::kFirstLiteralIndex * kPointerSize, | 4629 LiteralsArray::kFirstLiteralIndex * kPointerSize, |
4652 CodeStubAssembler::SMI_PARAMETERS); | 4630 CodeStubAssembler::SMI_PARAMETERS); |
4653 Node* undefined = assembler->UndefinedConstant(); | 4631 assembler->GotoIf(assembler->IsUndefined(allocation_site), call_runtime); |
4654 assembler->GotoIf(assembler->WordEqual(allocation_site, undefined), | |
4655 call_runtime); | |
4656 | 4632 |
4657 // Calculate the object and allocation size based on the properties count. | 4633 // Calculate the object and allocation size based on the properties count. |
4658 Node* object_size = assembler->IntPtrAdd( | 4634 Node* object_size = assembler->IntPtrAdd( |
4659 assembler->WordShl(properties_count, kPointerSizeLog2), | 4635 assembler->WordShl(properties_count, kPointerSizeLog2), |
4660 assembler->IntPtrConstant(JSObject::kHeaderSize)); | 4636 assembler->IntPtrConstant(JSObject::kHeaderSize)); |
4661 Node* allocation_size = object_size; | 4637 Node* allocation_size = object_size; |
4662 if (FLAG_allocation_site_pretenuring) { | 4638 if (FLAG_allocation_site_pretenuring) { |
4663 allocation_size = assembler->IntPtrAdd( | 4639 allocation_size = assembler->IntPtrAdd( |
4664 object_size, assembler->IntPtrConstant(AllocationMemento::kSize)); | 4640 object_size, assembler->IntPtrConstant(AllocationMemento::kSize)); |
4665 } | 4641 } |
(...skipping 618 matching lines...) Loading... |
5284 compiler::Node* flags, | 5260 compiler::Node* flags, |
5285 compiler::Node* context) { | 5261 compiler::Node* context) { |
5286 typedef CodeStubAssembler::Label Label; | 5262 typedef CodeStubAssembler::Label Label; |
5287 typedef CodeStubAssembler::Variable Variable; | 5263 typedef CodeStubAssembler::Variable Variable; |
5288 typedef compiler::Node Node; | 5264 typedef compiler::Node Node; |
5289 | 5265 |
5290 Label call_runtime(assembler, Label::kDeferred), end(assembler); | 5266 Label call_runtime(assembler, Label::kDeferred), end(assembler); |
5291 | 5267 |
5292 Variable result(assembler, MachineRepresentation::kTagged); | 5268 Variable result(assembler, MachineRepresentation::kTagged); |
5293 | 5269 |
5294 Node* undefined = assembler->UndefinedConstant(); | |
5295 Node* literals_array = | 5270 Node* literals_array = |
5296 assembler->LoadObjectField(closure, JSFunction::kLiteralsOffset); | 5271 assembler->LoadObjectField(closure, JSFunction::kLiteralsOffset); |
5297 Node* boilerplate = assembler->LoadFixedArrayElement( | 5272 Node* boilerplate = assembler->LoadFixedArrayElement( |
5298 literals_array, literal_index, | 5273 literals_array, literal_index, |
5299 LiteralsArray::kFirstLiteralIndex * kPointerSize, | 5274 LiteralsArray::kFirstLiteralIndex * kPointerSize, |
5300 CodeStubAssembler::SMI_PARAMETERS); | 5275 CodeStubAssembler::SMI_PARAMETERS); |
5301 assembler->GotoIf(assembler->WordEqual(boilerplate, undefined), | 5276 assembler->GotoIf(assembler->IsUndefined(boilerplate), &call_runtime); |
5302 &call_runtime); | |
5303 | 5277 |
5304 { | 5278 { |
5305 int size = JSRegExp::kSize + JSRegExp::kInObjectFieldCount * kPointerSize; | 5279 int size = JSRegExp::kSize + JSRegExp::kInObjectFieldCount * kPointerSize; |
5306 Node* copy = assembler->Allocate(size); | 5280 Node* copy = assembler->Allocate(size); |
5307 for (int offset = 0; offset < size; offset += kPointerSize) { | 5281 for (int offset = 0; offset < size; offset += kPointerSize) { |
5308 Node* value = assembler->LoadObjectField(boilerplate, offset); | 5282 Node* value = assembler->LoadObjectField(boilerplate, offset); |
5309 assembler->StoreObjectFieldNoWriteBarrier(copy, offset, value); | 5283 assembler->StoreObjectFieldNoWriteBarrier(copy, offset, value); |
5310 } | 5284 } |
5311 result.Bind(copy); | 5285 result.Bind(copy); |
5312 assembler->Goto(&end); | 5286 assembler->Goto(&end); |
(...skipping 84 matching lines...) Loading... |
5397 fast_elements(assembler), return_result(assembler); | 5371 fast_elements(assembler), return_result(assembler); |
5398 Variable result(assembler, MachineRepresentation::kTagged); | 5372 Variable result(assembler, MachineRepresentation::kTagged); |
5399 | 5373 |
5400 Node* literals_array = | 5374 Node* literals_array = |
5401 assembler->LoadObjectField(closure, JSFunction::kLiteralsOffset); | 5375 assembler->LoadObjectField(closure, JSFunction::kLiteralsOffset); |
5402 Node* allocation_site = assembler->LoadFixedArrayElement( | 5376 Node* allocation_site = assembler->LoadFixedArrayElement( |
5403 literals_array, literal_index, | 5377 literals_array, literal_index, |
5404 LiteralsArray::kFirstLiteralIndex * kPointerSize, | 5378 LiteralsArray::kFirstLiteralIndex * kPointerSize, |
5405 CodeStubAssembler::SMI_PARAMETERS); | 5379 CodeStubAssembler::SMI_PARAMETERS); |
5406 | 5380 |
5407 Node* undefined = assembler->UndefinedConstant(); | 5381 assembler->GotoIf(assembler->IsUndefined(allocation_site), call_runtime); |
5408 assembler->GotoIf(assembler->WordEqual(allocation_site, undefined), | |
5409 call_runtime); | |
5410 allocation_site = assembler->LoadFixedArrayElement( | 5382 allocation_site = assembler->LoadFixedArrayElement( |
5411 literals_array, literal_index, | 5383 literals_array, literal_index, |
5412 LiteralsArray::kFirstLiteralIndex * kPointerSize, | 5384 LiteralsArray::kFirstLiteralIndex * kPointerSize, |
5413 CodeStubAssembler::SMI_PARAMETERS); | 5385 CodeStubAssembler::SMI_PARAMETERS); |
5414 | 5386 |
5415 Node* boilerplate = assembler->LoadObjectField( | 5387 Node* boilerplate = assembler->LoadObjectField( |
5416 allocation_site, AllocationSite::kTransitionInfoOffset); | 5388 allocation_site, AllocationSite::kTransitionInfoOffset); |
5417 Node* boilerplate_map = assembler->LoadMap(boilerplate); | 5389 Node* boilerplate_map = assembler->LoadMap(boilerplate); |
5418 Node* boilerplate_elements = assembler->LoadElements(boilerplate); | 5390 Node* boilerplate_elements = assembler->LoadElements(boilerplate); |
5419 Node* capacity = assembler->LoadFixedArrayBaseLength(boilerplate_elements); | 5391 Node* capacity = assembler->LoadFixedArrayBaseLength(boilerplate_elements); |
5420 allocation_site = | 5392 allocation_site = |
5421 allocation_site_mode == TRACK_ALLOCATION_SITE ? allocation_site : nullptr; | 5393 allocation_site_mode == TRACK_ALLOCATION_SITE ? allocation_site : nullptr; |
5422 | 5394 |
5423 Node* zero = assembler->SmiConstant(Smi::FromInt(0)); | 5395 Node* zero = assembler->SmiConstant(Smi::FromInt(0)); |
5424 assembler->GotoIf(assembler->SmiEqual(capacity, zero), &zero_capacity); | 5396 assembler->GotoIf(assembler->SmiEqual(capacity, zero), &zero_capacity); |
5425 | 5397 |
5426 Node* elements_map = assembler->LoadMap(boilerplate_elements); | 5398 Node* elements_map = assembler->LoadMap(boilerplate_elements); |
5427 assembler->GotoIf( | 5399 assembler->GotoIf(assembler->IsFixedCOWArrayMap(elements_map), &cow_elements); |
5428 assembler->WordEqual(elements_map, assembler->FixedCowArrayMapConstant()), | |
5429 &cow_elements); | |
5430 | 5400 |
5431 assembler->GotoIf( | 5401 assembler->GotoIf(assembler->IsFixedArrayMap(elements_map), &fast_elements); |
5432 assembler->WordEqual(elements_map, assembler->FixedArrayMapConstant()), | |
5433 &fast_elements); | |
5434 { | 5402 { |
5435 assembler->Comment("fast double elements path"); | 5403 assembler->Comment("fast double elements path"); |
5436 if (FLAG_debug_code) { | 5404 if (FLAG_debug_code) { |
5437 Label correct_elements_map(assembler), abort(assembler, Label::kDeferred); | 5405 Label correct_elements_map(assembler), abort(assembler, Label::kDeferred); |
5438 assembler->BranchIf( | 5406 assembler->BranchIf(assembler->IsFixedDoubleArrayMap(elements_map), |
5439 assembler->WordEqual(elements_map, | 5407 &correct_elements_map, &abort); |
5440 assembler->FixedDoubleArrayMapConstant()), | |
5441 &correct_elements_map, &abort); | |
5442 | 5408 |
5443 assembler->Bind(&abort); | 5409 assembler->Bind(&abort); |
5444 { | 5410 { |
5445 Node* abort_id = assembler->SmiConstant( | 5411 Node* abort_id = assembler->SmiConstant( |
5446 Smi::FromInt(BailoutReason::kExpectedFixedDoubleArrayMap)); | 5412 Smi::FromInt(BailoutReason::kExpectedFixedDoubleArrayMap)); |
5447 assembler->TailCallRuntime(Runtime::kAbort, context, abort_id); | 5413 assembler->TailCallRuntime(Runtime::kAbort, context, abort_id); |
5448 } | 5414 } |
5449 assembler->Bind(&correct_elements_map); | 5415 assembler->Bind(&correct_elements_map); |
5450 } | 5416 } |
5451 | 5417 |
(...skipping 454 matching lines...) Loading... |
5906 | 5872 |
5907 if (type == MachineType::Pointer()) { | 5873 if (type == MachineType::Pointer()) { |
5908 return Representation::External(); | 5874 return Representation::External(); |
5909 } | 5875 } |
5910 | 5876 |
5911 return Representation::Tagged(); | 5877 return Representation::Tagged(); |
5912 } | 5878 } |
5913 | 5879 |
5914 } // namespace internal | 5880 } // namespace internal |
5915 } // namespace v8 | 5881 } // namespace v8 |
OLD | NEW |