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 <limits.h> // For LONG_MIN, LONG_MAX. | 5 #include <limits.h> // For LONG_MIN, LONG_MAX. |
6 | 6 |
7 #include "src/v8.h" | 7 #include "src/v8.h" |
8 | 8 |
9 #if V8_TARGET_ARCH_MIPS64 | 9 #if V8_TARGET_ARCH_MIPS64 |
10 | 10 |
(...skipping 3388 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3399 | 3399 |
3400 // Set the map, length and hash field. | 3400 // Set the map, length and hash field. |
3401 InitializeNewString(result, | 3401 InitializeNewString(result, |
3402 length, | 3402 length, |
3403 Heap::kStringMapRootIndex, | 3403 Heap::kStringMapRootIndex, |
3404 scratch1, | 3404 scratch1, |
3405 scratch2); | 3405 scratch2); |
3406 } | 3406 } |
3407 | 3407 |
3408 | 3408 |
3409 void MacroAssembler::AllocateAsciiString(Register result, | 3409 void MacroAssembler::AllocateOneByteString(Register result, Register length, |
3410 Register length, | 3410 Register scratch1, Register scratch2, |
3411 Register scratch1, | 3411 Register scratch3, |
3412 Register scratch2, | 3412 Label* gc_required) { |
3413 Register scratch3, | |
3414 Label* gc_required) { | |
3415 // Calculate the number of bytes needed for the characters in the string | 3413 // Calculate the number of bytes needed for the characters in the string |
3416 // while observing object alignment. | 3414 // while observing object alignment. |
3417 DCHECK((SeqOneByteString::kHeaderSize & kObjectAlignmentMask) == 0); | 3415 DCHECK((SeqOneByteString::kHeaderSize & kObjectAlignmentMask) == 0); |
3418 DCHECK(kCharSize == 1); | 3416 DCHECK(kCharSize == 1); |
3419 daddiu(scratch1, length, | 3417 daddiu(scratch1, length, |
3420 kObjectAlignmentMask + SeqOneByteString::kHeaderSize); | 3418 kObjectAlignmentMask + SeqOneByteString::kHeaderSize); |
3421 And(scratch1, scratch1, Operand(~kObjectAlignmentMask)); | 3419 And(scratch1, scratch1, Operand(~kObjectAlignmentMask)); |
3422 | 3420 |
3423 // Allocate ASCII string in new space. | 3421 // Allocate one-byte string in new space. |
3424 Allocate(scratch1, | 3422 Allocate(scratch1, |
3425 result, | 3423 result, |
3426 scratch2, | 3424 scratch2, |
3427 scratch3, | 3425 scratch3, |
3428 gc_required, | 3426 gc_required, |
3429 TAG_OBJECT); | 3427 TAG_OBJECT); |
3430 | 3428 |
3431 // Set the map, length and hash field. | 3429 // Set the map, length and hash field. |
3432 InitializeNewString(result, | 3430 InitializeNewString(result, length, Heap::kOneByteStringMapRootIndex, |
3433 length, | 3431 scratch1, scratch2); |
3434 Heap::kAsciiStringMapRootIndex, | |
3435 scratch1, | |
3436 scratch2); | |
3437 } | 3432 } |
3438 | 3433 |
3439 | 3434 |
3440 void MacroAssembler::AllocateTwoByteConsString(Register result, | 3435 void MacroAssembler::AllocateTwoByteConsString(Register result, |
3441 Register length, | 3436 Register length, |
3442 Register scratch1, | 3437 Register scratch1, |
3443 Register scratch2, | 3438 Register scratch2, |
3444 Label* gc_required) { | 3439 Label* gc_required) { |
3445 Allocate(ConsString::kSize, result, scratch1, scratch2, gc_required, | 3440 Allocate(ConsString::kSize, result, scratch1, scratch2, gc_required, |
3446 TAG_OBJECT); | 3441 TAG_OBJECT); |
3447 InitializeNewString(result, | 3442 InitializeNewString(result, |
3448 length, | 3443 length, |
3449 Heap::kConsStringMapRootIndex, | 3444 Heap::kConsStringMapRootIndex, |
3450 scratch1, | 3445 scratch1, |
3451 scratch2); | 3446 scratch2); |
3452 } | 3447 } |
3453 | 3448 |
3454 | 3449 |
3455 void MacroAssembler::AllocateAsciiConsString(Register result, | 3450 void MacroAssembler::AllocateOneByteConsString(Register result, Register length, |
3456 Register length, | 3451 Register scratch1, |
3457 Register scratch1, | 3452 Register scratch2, |
3458 Register scratch2, | 3453 Label* gc_required) { |
3459 Label* gc_required) { | |
3460 Allocate(ConsString::kSize, | 3454 Allocate(ConsString::kSize, |
3461 result, | 3455 result, |
3462 scratch1, | 3456 scratch1, |
3463 scratch2, | 3457 scratch2, |
3464 gc_required, | 3458 gc_required, |
3465 TAG_OBJECT); | 3459 TAG_OBJECT); |
3466 | 3460 |
3467 InitializeNewString(result, | 3461 InitializeNewString(result, length, Heap::kConsOneByteStringMapRootIndex, |
3468 length, | 3462 scratch1, scratch2); |
3469 Heap::kConsAsciiStringMapRootIndex, | |
3470 scratch1, | |
3471 scratch2); | |
3472 } | 3463 } |
3473 | 3464 |
3474 | 3465 |
3475 void MacroAssembler::AllocateTwoByteSlicedString(Register result, | 3466 void MacroAssembler::AllocateTwoByteSlicedString(Register result, |
3476 Register length, | 3467 Register length, |
3477 Register scratch1, | 3468 Register scratch1, |
3478 Register scratch2, | 3469 Register scratch2, |
3479 Label* gc_required) { | 3470 Label* gc_required) { |
3480 Allocate(SlicedString::kSize, result, scratch1, scratch2, gc_required, | 3471 Allocate(SlicedString::kSize, result, scratch1, scratch2, gc_required, |
3481 TAG_OBJECT); | 3472 TAG_OBJECT); |
3482 | 3473 |
3483 InitializeNewString(result, | 3474 InitializeNewString(result, |
3484 length, | 3475 length, |
3485 Heap::kSlicedStringMapRootIndex, | 3476 Heap::kSlicedStringMapRootIndex, |
3486 scratch1, | 3477 scratch1, |
3487 scratch2); | 3478 scratch2); |
3488 } | 3479 } |
3489 | 3480 |
3490 | 3481 |
3491 void MacroAssembler::AllocateAsciiSlicedString(Register result, | 3482 void MacroAssembler::AllocateOneByteSlicedString(Register result, |
3492 Register length, | 3483 Register length, |
3493 Register scratch1, | 3484 Register scratch1, |
3494 Register scratch2, | 3485 Register scratch2, |
3495 Label* gc_required) { | 3486 Label* gc_required) { |
3496 Allocate(SlicedString::kSize, result, scratch1, scratch2, gc_required, | 3487 Allocate(SlicedString::kSize, result, scratch1, scratch2, gc_required, |
3497 TAG_OBJECT); | 3488 TAG_OBJECT); |
3498 | 3489 |
3499 InitializeNewString(result, | 3490 InitializeNewString(result, length, Heap::kSlicedOneByteStringMapRootIndex, |
3500 length, | 3491 scratch1, scratch2); |
3501 Heap::kSlicedAsciiStringMapRootIndex, | |
3502 scratch1, | |
3503 scratch2); | |
3504 } | 3492 } |
3505 | 3493 |
3506 | 3494 |
3507 void MacroAssembler::JumpIfNotUniqueName(Register reg, | 3495 void MacroAssembler::JumpIfNotUniqueName(Register reg, |
3508 Label* not_unique_name) { | 3496 Label* not_unique_name) { |
3509 STATIC_ASSERT(kInternalizedTag == 0 && kStringTag == 0); | 3497 STATIC_ASSERT(kInternalizedTag == 0 && kStringTag == 0); |
3510 Label succeed; | 3498 Label succeed; |
3511 And(at, reg, Operand(kIsNotStringMask | kIsNotInternalizedMask)); | 3499 And(at, reg, Operand(kIsNotStringMask | kIsNotInternalizedMask)); |
3512 Branch(&succeed, eq, at, Operand(zero_reg)); | 3500 Branch(&succeed, eq, at, Operand(zero_reg)); |
3513 Branch(not_unique_name, ne, reg, Operand(SYMBOL_TYPE)); | 3501 Branch(not_unique_name, ne, reg, Operand(SYMBOL_TYPE)); |
(...skipping 1780 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5294 bind(&load_result_from_cache); | 5282 bind(&load_result_from_cache); |
5295 ld(result, FieldMemOperand(scratch, FixedArray::kHeaderSize + kPointerSize)); | 5283 ld(result, FieldMemOperand(scratch, FixedArray::kHeaderSize + kPointerSize)); |
5296 | 5284 |
5297 IncrementCounter(isolate()->counters()->number_to_string_native(), | 5285 IncrementCounter(isolate()->counters()->number_to_string_native(), |
5298 1, | 5286 1, |
5299 scratch1, | 5287 scratch1, |
5300 scratch2); | 5288 scratch2); |
5301 } | 5289 } |
5302 | 5290 |
5303 | 5291 |
5304 void MacroAssembler::JumpIfNonSmisNotBothSequentialAsciiStrings( | 5292 void MacroAssembler::JumpIfNonSmisNotBothSequentialOneByteStrings( |
5305 Register first, | 5293 Register first, Register second, Register scratch1, Register scratch2, |
5306 Register second, | |
5307 Register scratch1, | |
5308 Register scratch2, | |
5309 Label* failure) { | 5294 Label* failure) { |
5310 // Test that both first and second are sequential ASCII strings. | 5295 // Test that both first and second are sequential one-byte strings. |
5311 // Assume that they are non-smis. | 5296 // Assume that they are non-smis. |
5312 ld(scratch1, FieldMemOperand(first, HeapObject::kMapOffset)); | 5297 ld(scratch1, FieldMemOperand(first, HeapObject::kMapOffset)); |
5313 ld(scratch2, FieldMemOperand(second, HeapObject::kMapOffset)); | 5298 ld(scratch2, FieldMemOperand(second, HeapObject::kMapOffset)); |
5314 lbu(scratch1, FieldMemOperand(scratch1, Map::kInstanceTypeOffset)); | 5299 lbu(scratch1, FieldMemOperand(scratch1, Map::kInstanceTypeOffset)); |
5315 lbu(scratch2, FieldMemOperand(scratch2, Map::kInstanceTypeOffset)); | 5300 lbu(scratch2, FieldMemOperand(scratch2, Map::kInstanceTypeOffset)); |
5316 | 5301 |
5317 JumpIfBothInstanceTypesAreNotSequentialAscii(scratch1, | 5302 JumpIfBothInstanceTypesAreNotSequentialOneByte(scratch1, scratch2, scratch1, |
5318 scratch2, | 5303 scratch2, failure); |
5319 scratch1, | |
5320 scratch2, | |
5321 failure); | |
5322 } | 5304 } |
5323 | 5305 |
5324 | 5306 |
5325 void MacroAssembler::JumpIfNotBothSequentialAsciiStrings(Register first, | 5307 void MacroAssembler::JumpIfNotBothSequentialOneByteStrings(Register first, |
5326 Register second, | 5308 Register second, |
5327 Register scratch1, | 5309 Register scratch1, |
5328 Register scratch2, | 5310 Register scratch2, |
5329 Label* failure) { | 5311 Label* failure) { |
5330 // Check that neither is a smi. | 5312 // Check that neither is a smi. |
5331 STATIC_ASSERT(kSmiTag == 0); | 5313 STATIC_ASSERT(kSmiTag == 0); |
5332 And(scratch1, first, Operand(second)); | 5314 And(scratch1, first, Operand(second)); |
5333 JumpIfSmi(scratch1, failure); | 5315 JumpIfSmi(scratch1, failure); |
5334 JumpIfNonSmisNotBothSequentialAsciiStrings(first, | 5316 JumpIfNonSmisNotBothSequentialOneByteStrings(first, second, scratch1, |
5335 second, | 5317 scratch2, failure); |
5336 scratch1, | |
5337 scratch2, | |
5338 failure); | |
5339 } | 5318 } |
5340 | 5319 |
5341 | 5320 |
5342 void MacroAssembler::JumpIfBothInstanceTypesAreNotSequentialAscii( | 5321 void MacroAssembler::JumpIfBothInstanceTypesAreNotSequentialOneByte( |
5343 Register first, | 5322 Register first, Register second, Register scratch1, Register scratch2, |
5344 Register second, | |
5345 Register scratch1, | |
5346 Register scratch2, | |
5347 Label* failure) { | 5323 Label* failure) { |
5348 const int kFlatAsciiStringMask = | 5324 const int kFlatOneByteStringMask = |
5349 kIsNotStringMask | kStringEncodingMask | kStringRepresentationMask; | 5325 kIsNotStringMask | kStringEncodingMask | kStringRepresentationMask; |
5350 const int kFlatAsciiStringTag = | 5326 const int kFlatOneByteStringTag = |
5351 kStringTag | kOneByteStringTag | kSeqStringTag; | 5327 kStringTag | kOneByteStringTag | kSeqStringTag; |
5352 DCHECK(kFlatAsciiStringTag <= 0xffff); // Ensure this fits 16-bit immed. | 5328 DCHECK(kFlatOneByteStringTag <= 0xffff); // Ensure this fits 16-bit immed. |
5353 andi(scratch1, first, kFlatAsciiStringMask); | 5329 andi(scratch1, first, kFlatOneByteStringMask); |
5354 Branch(failure, ne, scratch1, Operand(kFlatAsciiStringTag)); | 5330 Branch(failure, ne, scratch1, Operand(kFlatOneByteStringTag)); |
5355 andi(scratch2, second, kFlatAsciiStringMask); | 5331 andi(scratch2, second, kFlatOneByteStringMask); |
5356 Branch(failure, ne, scratch2, Operand(kFlatAsciiStringTag)); | 5332 Branch(failure, ne, scratch2, Operand(kFlatOneByteStringTag)); |
5357 } | 5333 } |
5358 | 5334 |
5359 | 5335 |
5360 void MacroAssembler::JumpIfInstanceTypeIsNotSequentialAscii(Register type, | 5336 void MacroAssembler::JumpIfInstanceTypeIsNotSequentialOneByte(Register type, |
5361 Register scratch, | 5337 Register scratch, |
5362 Label* failure) { | 5338 Label* failure) { |
5363 const int kFlatAsciiStringMask = | 5339 const int kFlatOneByteStringMask = |
5364 kIsNotStringMask | kStringEncodingMask | kStringRepresentationMask; | 5340 kIsNotStringMask | kStringEncodingMask | kStringRepresentationMask; |
5365 const int kFlatAsciiStringTag = | 5341 const int kFlatOneByteStringTag = |
5366 kStringTag | kOneByteStringTag | kSeqStringTag; | 5342 kStringTag | kOneByteStringTag | kSeqStringTag; |
5367 And(scratch, type, Operand(kFlatAsciiStringMask)); | 5343 And(scratch, type, Operand(kFlatOneByteStringMask)); |
5368 Branch(failure, ne, scratch, Operand(kFlatAsciiStringTag)); | 5344 Branch(failure, ne, scratch, Operand(kFlatOneByteStringTag)); |
5369 } | 5345 } |
5370 | 5346 |
5371 | 5347 |
5372 static const int kRegisterPassedArguments = (kMipsAbi == kN64) ? 8 : 4; | 5348 static const int kRegisterPassedArguments = (kMipsAbi == kN64) ? 8 : 4; |
5373 | 5349 |
5374 int MacroAssembler::CalculateStackPassedWords(int num_reg_arguments, | 5350 int MacroAssembler::CalculateStackPassedWords(int num_reg_arguments, |
5375 int num_double_arguments) { | 5351 int num_double_arguments) { |
5376 int stack_passed_words = 0; | 5352 int stack_passed_words = 0; |
5377 num_reg_arguments += 2 * num_double_arguments; | 5353 num_reg_arguments += 2 * num_double_arguments; |
5378 | 5354 |
(...skipping 404 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5783 DCHECK_EQ(0, kConsStringTag & kExternalStringTag); | 5759 DCHECK_EQ(0, kConsStringTag & kExternalStringTag); |
5784 And(t8, instance_type, Operand(kExternalStringTag)); | 5760 And(t8, instance_type, Operand(kExternalStringTag)); |
5785 { | 5761 { |
5786 Label skip; | 5762 Label skip; |
5787 Branch(&skip, eq, t8, Operand(zero_reg)); | 5763 Branch(&skip, eq, t8, Operand(zero_reg)); |
5788 li(length, ExternalString::kSize); | 5764 li(length, ExternalString::kSize); |
5789 Branch(&is_data_object); | 5765 Branch(&is_data_object); |
5790 bind(&skip); | 5766 bind(&skip); |
5791 } | 5767 } |
5792 | 5768 |
5793 // Sequential string, either ASCII or UC16. | 5769 // Sequential string, either Latin1 or UC16. |
5794 // For ASCII (char-size of 1) we shift the smi tag away to get the length. | 5770 // For Latin1 (char-size of 1) we shift the smi tag away to get the length. |
5795 // For UC16 (char-size of 2) we just leave the smi tag in place, thereby | 5771 // For UC16 (char-size of 2) we just leave the smi tag in place, thereby |
5796 // getting the length multiplied by 2. | 5772 // getting the length multiplied by 2. |
5797 DCHECK(kOneByteStringTag == 4 && kStringEncodingMask == 4); | 5773 DCHECK(kOneByteStringTag == 4 && kStringEncodingMask == 4); |
5798 DCHECK(kSmiTag == 0 && kSmiTagSize == 1); | 5774 DCHECK(kSmiTag == 0 && kSmiTagSize == 1); |
5799 lw(t9, UntagSmiFieldMemOperand(value, String::kLengthOffset)); | 5775 lw(t9, UntagSmiFieldMemOperand(value, String::kLengthOffset)); |
5800 And(t8, instance_type, Operand(kStringEncodingMask)); | 5776 And(t8, instance_type, Operand(kStringEncodingMask)); |
5801 { | 5777 { |
5802 Label skip; | 5778 Label skip; |
5803 Branch(&skip, ne, t8, Operand(zero_reg)); | 5779 Branch(&skip, ne, t8, Operand(zero_reg)); |
5804 // Adjust length for UC16. | 5780 // Adjust length for UC16. |
(...skipping 299 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6104 } | 6080 } |
6105 if (mag.shift > 0) sra(result, result, mag.shift); | 6081 if (mag.shift > 0) sra(result, result, mag.shift); |
6106 srl(at, dividend, 31); | 6082 srl(at, dividend, 31); |
6107 Addu(result, result, Operand(at)); | 6083 Addu(result, result, Operand(at)); |
6108 } | 6084 } |
6109 | 6085 |
6110 | 6086 |
6111 } } // namespace v8::internal | 6087 } } // namespace v8::internal |
6112 | 6088 |
6113 #endif // V8_TARGET_ARCH_MIPS64 | 6089 #endif // V8_TARGET_ARCH_MIPS64 |
OLD | NEW |