OLD | NEW |
---|---|
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 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 740 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
751 | 751 |
752 | 752 |
753 static MemOperand GenerateMappedArgumentsLookup(MacroAssembler* masm, | 753 static MemOperand GenerateMappedArgumentsLookup(MacroAssembler* masm, |
754 Register object, | 754 Register object, |
755 Register key, | 755 Register key, |
756 Register scratch1, | 756 Register scratch1, |
757 Register scratch2, | 757 Register scratch2, |
758 Register scratch3, | 758 Register scratch3, |
759 Label* unmapped_case, | 759 Label* unmapped_case, |
760 Label* slow_case) { | 760 Label* slow_case) { |
761 Heap* heap = masm->isolate()->heap(); | |
762 | |
763 // Check that the receiver is a JSObject. Because of the map check | 761 // Check that the receiver is a JSObject. Because of the map check |
764 // later, we do not need to check for interceptors or whether it | 762 // later, we do not need to check for interceptors or whether it |
765 // requires access checks. | 763 // requires access checks. |
766 __ JumpIfSmi(object, slow_case); | 764 __ JumpIfSmi(object, slow_case); |
767 // Check that the object is some kind of JSObject. | 765 // Check that the object is some kind of JSObject. |
768 __ GetObjectType(object, scratch1, scratch2); | 766 __ GetObjectType(object, scratch1, scratch2); |
769 __ Branch(slow_case, lt, scratch2, Operand(FIRST_JS_RECEIVER_TYPE)); | 767 __ Branch(slow_case, lt, scratch2, Operand(FIRST_JS_RECEIVER_TYPE)); |
770 | 768 |
771 // Check that the key is a positive smi. | 769 // Check that the key is a positive smi. |
772 __ And(scratch1, key, Operand(0x8000001)); | 770 __ And(scratch1, key, Operand(0x8000001)); |
773 __ Branch(slow_case, ne, scratch1, Operand(zero_reg)); | 771 __ Branch(slow_case, ne, scratch1, Operand(zero_reg)); |
774 | 772 |
775 // Load the elements into scratch1 and check its map. | 773 // Load the elements into scratch1 and check its map. |
776 Handle<Map> arguments_map(heap->non_strict_arguments_elements_map()); | |
777 __ lw(scratch1, FieldMemOperand(object, JSObject::kElementsOffset)); | 774 __ lw(scratch1, FieldMemOperand(object, JSObject::kElementsOffset)); |
778 __ CheckMap(scratch1, scratch2, arguments_map, slow_case, DONT_DO_SMI_CHECK); | 775 __ CheckMap(scratch1, scratch2, Heap::kNonStrictArgumentsElementsMapRootIndex, |
Erik Corry
2012/03/17 02:49:18
Arguments should be all on one line or one per lin
| |
779 | 776 slow_case, DONT_DO_SMI_CHECK); |
780 // Check if element is in the range of mapped arguments. If not, jump | 777 // Check if element is in the range of mapped arguments. If not, jump |
781 // to the unmapped lookup with the parameter map in scratch1. | 778 // to the unmapped lookup with the parameter map in scratch1. |
782 __ lw(scratch2, FieldMemOperand(scratch1, FixedArray::kLengthOffset)); | 779 __ lw(scratch2, FieldMemOperand(scratch1, FixedArray::kLengthOffset)); |
783 __ Subu(scratch2, scratch2, Operand(Smi::FromInt(2))); | 780 __ Subu(scratch2, scratch2, Operand(Smi::FromInt(2))); |
784 __ Branch(unmapped_case, Ugreater_equal, key, Operand(scratch2)); | 781 __ Branch(unmapped_case, Ugreater_equal, key, Operand(scratch2)); |
785 | 782 |
786 // Load element index and check whether it is the hole. | 783 // Load element index and check whether it is the hole. |
787 const int kOffset = | 784 const int kOffset = |
788 FixedArray::kHeaderSize + 2 * kPointerSize - kHeapObjectTag; | 785 FixedArray::kHeaderSize + 2 * kPointerSize - kHeapObjectTag; |
789 | 786 |
(...skipping 23 matching lines...) Expand all Loading... | |
813 Register parameter_map, | 810 Register parameter_map, |
814 Register scratch, | 811 Register scratch, |
815 Label* slow_case) { | 812 Label* slow_case) { |
816 // Element is in arguments backing store, which is referenced by the | 813 // Element is in arguments backing store, which is referenced by the |
817 // second element of the parameter_map. The parameter_map register | 814 // second element of the parameter_map. The parameter_map register |
818 // must be loaded with the parameter map of the arguments object and is | 815 // must be loaded with the parameter map of the arguments object and is |
819 // overwritten. | 816 // overwritten. |
820 const int kBackingStoreOffset = FixedArray::kHeaderSize + kPointerSize; | 817 const int kBackingStoreOffset = FixedArray::kHeaderSize + kPointerSize; |
821 Register backing_store = parameter_map; | 818 Register backing_store = parameter_map; |
822 __ lw(backing_store, FieldMemOperand(parameter_map, kBackingStoreOffset)); | 819 __ lw(backing_store, FieldMemOperand(parameter_map, kBackingStoreOffset)); |
823 Handle<Map> fixed_array_map(masm->isolate()->heap()->fixed_array_map()); | 820 __ CheckMap(backing_store, scratch, Heap::kFixedArrayMapRootIndex, slow_case, |
824 __ CheckMap(backing_store, scratch, fixed_array_map, slow_case, | 821 DONT_DO_SMI_CHECK); |
825 DONT_DO_SMI_CHECK); | |
826 __ lw(scratch, FieldMemOperand(backing_store, FixedArray::kLengthOffset)); | 822 __ lw(scratch, FieldMemOperand(backing_store, FixedArray::kLengthOffset)); |
827 __ Branch(slow_case, Ugreater_equal, key, Operand(scratch)); | 823 __ Branch(slow_case, Ugreater_equal, key, Operand(scratch)); |
828 __ li(scratch, Operand(kPointerSize >> 1)); | 824 __ li(scratch, Operand(kPointerSize >> 1)); |
829 __ mul(scratch, key, scratch); | 825 __ mul(scratch, key, scratch); |
830 __ Addu(scratch, | 826 __ Addu(scratch, |
831 scratch, | 827 scratch, |
832 Operand(FixedArray::kHeaderSize - kHeapObjectTag)); | 828 Operand(FixedArray::kHeaderSize - kHeapObjectTag)); |
833 __ Addu(scratch, backing_store, scratch); | 829 __ Addu(scratch, backing_store, scratch); |
834 return MemOperand(scratch); | 830 return MemOperand(scratch); |
835 } | 831 } |
(...skipping 411 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1247 __ bind(&extra); | 1243 __ bind(&extra); |
1248 // Condition code from comparing key and array length is still available. | 1244 // Condition code from comparing key and array length is still available. |
1249 // Only support writing to array[array.length]. | 1245 // Only support writing to array[array.length]. |
1250 __ Branch(&slow, ne, key, Operand(t0)); | 1246 __ Branch(&slow, ne, key, Operand(t0)); |
1251 // Check for room in the elements backing store. | 1247 // Check for room in the elements backing store. |
1252 // Both the key and the length of FixedArray are smis. | 1248 // Both the key and the length of FixedArray are smis. |
1253 __ lw(t0, FieldMemOperand(elements, FixedArray::kLengthOffset)); | 1249 __ lw(t0, FieldMemOperand(elements, FixedArray::kLengthOffset)); |
1254 __ Branch(&slow, hs, key, Operand(t0)); | 1250 __ Branch(&slow, hs, key, Operand(t0)); |
1255 __ lw(elements_map, FieldMemOperand(elements, HeapObject::kMapOffset)); | 1251 __ lw(elements_map, FieldMemOperand(elements, HeapObject::kMapOffset)); |
1256 __ Branch(&check_if_double_array, ne, elements_map, | 1252 __ Branch(&check_if_double_array, ne, elements_map, |
1257 Operand(masm->isolate()->factory()->fixed_array_map())); | 1253 Heap::kFixedArrayMapRootIndex); |
1254 | |
1258 // Calculate key + 1 as smi. | 1255 // Calculate key + 1 as smi. |
1259 STATIC_ASSERT(kSmiTag == 0); | 1256 STATIC_ASSERT(kSmiTag == 0); |
1260 __ Addu(t0, key, Operand(Smi::FromInt(1))); | 1257 __ Addu(t0, key, Operand(Smi::FromInt(1))); |
1261 __ sw(t0, FieldMemOperand(receiver, JSArray::kLengthOffset)); | 1258 __ sw(t0, FieldMemOperand(receiver, JSArray::kLengthOffset)); |
1262 __ Branch(&fast_object_without_map_check); | 1259 __ Branch(&fast_object_without_map_check); |
1263 | 1260 |
1264 __ bind(&check_if_double_array); | 1261 __ bind(&check_if_double_array); |
1265 __ Branch(&slow, ne, elements_map, | 1262 __ Branch(&slow, ne, elements_map, Heap::kFixedDoubleArrayMapRootIndex); |
1266 Operand(masm->isolate()->factory()->fixed_double_array_map())); | |
1267 // Add 1 to key, and go to common element store code for doubles. | 1263 // Add 1 to key, and go to common element store code for doubles. |
1268 STATIC_ASSERT(kSmiTag == 0); | 1264 STATIC_ASSERT(kSmiTag == 0); |
1269 __ Addu(t0, key, Operand(Smi::FromInt(1))); | 1265 __ Addu(t0, key, Operand(Smi::FromInt(1))); |
1270 __ sw(t0, FieldMemOperand(receiver, JSArray::kLengthOffset)); | 1266 __ sw(t0, FieldMemOperand(receiver, JSArray::kLengthOffset)); |
1271 __ jmp(&fast_double_without_map_check); | 1267 __ jmp(&fast_double_without_map_check); |
1272 | 1268 |
1273 // Array case: Get the length and the elements array from the JS | 1269 // Array case: Get the length and the elements array from the JS |
1274 // array. Check that the array is in fast mode (and writable); if it | 1270 // array. Check that the array is in fast mode (and writable); if it |
1275 // is the length is always a smi. | 1271 // is the length is always a smi. |
1276 __ bind(&array); | 1272 __ bind(&array); |
1277 __ lw(elements, FieldMemOperand(receiver, JSObject::kElementsOffset)); | 1273 __ lw(elements, FieldMemOperand(receiver, JSObject::kElementsOffset)); |
1278 | 1274 |
1279 // Check the key against the length in the array. | 1275 // Check the key against the length in the array. |
1280 __ lw(t0, FieldMemOperand(receiver, JSArray::kLengthOffset)); | 1276 __ lw(t0, FieldMemOperand(receiver, JSArray::kLengthOffset)); |
1281 __ Branch(&extra, hs, key, Operand(t0)); | 1277 __ Branch(&extra, hs, key, Operand(t0)); |
1282 // Fall through to fast case. | 1278 // Fall through to fast case. |
1283 | 1279 |
1284 __ bind(&fast_object_with_map_check); | 1280 __ bind(&fast_object_with_map_check); |
1285 Register scratch_value = t0; | 1281 Register scratch_value = t0; |
1286 Register address = t1; | 1282 Register address = t1; |
1287 __ lw(elements_map, FieldMemOperand(elements, HeapObject::kMapOffset)); | 1283 __ lw(elements_map, FieldMemOperand(elements, HeapObject::kMapOffset)); |
1288 __ Branch(&fast_double_with_map_check, ne, elements_map, | 1284 __ Branch(&fast_double_with_map_check, ne, elements_map, |
1289 Operand(masm->isolate()->factory()->fixed_array_map())); | 1285 Heap::kFixedArrayMapRootIndex); |
1290 __ bind(&fast_object_without_map_check); | 1286 __ bind(&fast_object_without_map_check); |
1291 // Smi stores don't require further checks. | 1287 // Smi stores don't require further checks. |
1292 Label non_smi_value; | 1288 Label non_smi_value; |
1293 __ JumpIfNotSmi(value, &non_smi_value); | 1289 __ JumpIfNotSmi(value, &non_smi_value); |
1294 // It's irrelevant whether array is smi-only or not when writing a smi. | 1290 // It's irrelevant whether array is smi-only or not when writing a smi. |
1295 __ Addu(address, elements, Operand(FixedArray::kHeaderSize - kHeapObjectTag)); | 1291 __ Addu(address, elements, Operand(FixedArray::kHeaderSize - kHeapObjectTag)); |
1296 __ sll(scratch_value, key, kPointerSizeLog2 - kSmiTagSize); | 1292 __ sll(scratch_value, key, kPointerSizeLog2 - kSmiTagSize); |
1297 __ Addu(address, address, scratch_value); | 1293 __ Addu(address, address, scratch_value); |
1298 __ sw(value, MemOperand(address)); | 1294 __ sw(value, MemOperand(address)); |
1299 __ Ret(USE_DELAY_SLOT); | 1295 __ Ret(USE_DELAY_SLOT); |
(...skipping 16 matching lines...) Expand all Loading... | |
1316 value, | 1312 value, |
1317 kRAHasNotBeenSaved, | 1313 kRAHasNotBeenSaved, |
1318 kDontSaveFPRegs, | 1314 kDontSaveFPRegs, |
1319 EMIT_REMEMBERED_SET, | 1315 EMIT_REMEMBERED_SET, |
1320 OMIT_SMI_CHECK); | 1316 OMIT_SMI_CHECK); |
1321 __ Ret(); | 1317 __ Ret(); |
1322 | 1318 |
1323 __ bind(&fast_double_with_map_check); | 1319 __ bind(&fast_double_with_map_check); |
1324 // Check for fast double array case. If this fails, call through to the | 1320 // Check for fast double array case. If this fails, call through to the |
1325 // runtime. | 1321 // runtime. |
1326 __ Branch(&slow, ne, elements_map, | 1322 __ Branch(&slow, ne, elements_map, Heap::kFixedDoubleArrayMapRootIndex); |
1327 Operand(masm->isolate()->factory()->fixed_double_array_map())); | |
1328 __ bind(&fast_double_without_map_check); | 1323 __ bind(&fast_double_without_map_check); |
1329 __ StoreNumberToDoubleElements(value, | 1324 __ StoreNumberToDoubleElements(value, |
1330 key, | 1325 key, |
1331 receiver, | 1326 receiver, |
1332 elements, | 1327 elements, |
1333 a3, | 1328 a3, |
1334 t0, | 1329 t0, |
1335 t1, | 1330 t1, |
1336 t2, | 1331 t2, |
1337 &transition_double_elements); | 1332 &transition_double_elements); |
(...skipping 414 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1752 Register reg = Register::from_code(Assembler::GetRs(instr_at_patch)); | 1747 Register reg = Register::from_code(Assembler::GetRs(instr_at_patch)); |
1753 patcher.masm()->andi(at, reg, kSmiTagMask); | 1748 patcher.masm()->andi(at, reg, kSmiTagMask); |
1754 patcher.ChangeBranchCondition(eq); | 1749 patcher.ChangeBranchCondition(eq); |
1755 } | 1750 } |
1756 } | 1751 } |
1757 | 1752 |
1758 | 1753 |
1759 } } // namespace v8::internal | 1754 } } // namespace v8::internal |
1760 | 1755 |
1761 #endif // V8_TARGET_ARCH_MIPS | 1756 #endif // V8_TARGET_ARCH_MIPS |
OLD | NEW |