Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2006-2008 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2008 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 510 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 521 case kConsStringTag: { | 521 case kConsStringTag: { |
| 522 ConsString* cs = ConsString::cast(this); | 522 ConsString* cs = ConsString::cast(this); |
| 523 if (String::cast(cs->second())->length() == 0) { | 523 if (String::cast(cs->second())->length() == 0) { |
| 524 return this; | 524 return this; |
| 525 } | 525 } |
| 526 // There's little point in putting the flat string in new space if the | 526 // There's little point in putting the flat string in new space if the |
| 527 // cons string is in old space. It can never get GCed until there is | 527 // cons string is in old space. It can never get GCed until there is |
| 528 // an old space GC. | 528 // an old space GC. |
| 529 PretenureFlag tenure = Heap::InNewSpace(this) ? NOT_TENURED : TENURED; | 529 PretenureFlag tenure = Heap::InNewSpace(this) ? NOT_TENURED : TENURED; |
| 530 int len = length(); | 530 int len = length(); |
| 531 Object* object = IsAsciiRepresentation() ? | 531 Object* object; |
| 532 Heap::AllocateRawAsciiString(len, tenure) : | 532 String* result; |
| 533 Heap::AllocateRawTwoByteString(len, tenure); | 533 if (IsAsciiRepresentation()) { |
| 534 if (object->IsFailure()) return object; | 534 object = Heap::AllocateRawAsciiString(len, tenure); |
| 535 String* result = String::cast(object); | 535 if (object->IsFailure()) return object; |
| 536 Flatten(this, result, 0, len, 0); | 536 result = String::cast(object); |
| 537 String* first = String::cast(cs->first()); | |
| 538 int first_length = first->length(); | |
| 539 byte* dest = SeqAsciiString::cast(result)->GetCharsAddress(); | |
| 540 WriteToFlat(first, dest, 0, first_length); | |
| 541 WriteToFlat(String::cast(cs->second()), dest + first_length, 0, len - fi rst_length); | |
| 542 } else { | |
| 543 object = Heap::AllocateRawTwoByteString(len, tenure); | |
| 544 if (object->IsFailure()) return object; | |
| 545 result = String::cast(object); | |
| 546 uc16* dest = reinterpret_cast<uc16*>( | |
| 547 SeqTwoByteString::cast(result)->GetCharsAddress()); | |
|
Christian Plesner Hansen
2008/10/21 14:16:22
Maybe add an accessor on seq two byte string that
Erik Corry
2008/10/22 11:59:48
Good idea.
| |
| 548 String* first = String::cast(cs->first()); | |
| 549 int first_length = first->length(); | |
| 550 WriteToFlat(first, dest, 0, first_length); | |
| 551 WriteToFlat(String::cast(cs->second()), dest + first_length, 0, len - fi rst_length); | |
| 552 } | |
| 537 cs->set_first(result); | 553 cs->set_first(result); |
| 538 cs->set_second(Heap::empty_string()); | 554 cs->set_second(Heap::empty_string()); |
| 539 return this; | 555 return this; |
| 540 } | 556 } |
| 541 default: | 557 default: |
| 542 return this; | 558 return this; |
| 543 } | 559 } |
| 544 } | 560 } |
| 545 | 561 |
| 546 | 562 |
| (...skipping 2315 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2862 TryFlatten(); | 2878 TryFlatten(); |
| 2863 Access<StringInputBuffer> buffer(&string_input_buffer); | 2879 Access<StringInputBuffer> buffer(&string_input_buffer); |
| 2864 buffer->Reset(0, this); | 2880 buffer->Reset(0, this); |
| 2865 int result = 0; | 2881 int result = 0; |
| 2866 while (buffer->has_more()) | 2882 while (buffer->has_more()) |
| 2867 result += unibrow::Utf8::Length(buffer->GetNext()); | 2883 result += unibrow::Utf8::Length(buffer->GetNext()); |
| 2868 return result; | 2884 return result; |
| 2869 } | 2885 } |
| 2870 | 2886 |
| 2871 | 2887 |
| 2872 Vector<const char> String::ToAsciiVector() { | 2888 Vector<const byte> String::ToAsciiVector() { |
| 2873 ASSERT(IsAsciiRepresentation()); | 2889 ASSERT(IsAsciiRepresentation()); |
| 2874 ASSERT(IsFlat()); | 2890 ASSERT(IsFlat()); |
| 2875 | 2891 |
| 2876 int offset = 0; | 2892 int offset = 0; |
| 2877 int length = this->length(); | 2893 int length = this->length(); |
| 2878 StringRepresentationTag string_tag = representation_tag(); | 2894 StringRepresentationTag string_tag = representation_tag(); |
| 2879 String* string = this; | 2895 String* string = this; |
| 2880 if (string_tag == kSlicedStringTag) { | 2896 if (string_tag == kSlicedStringTag) { |
| 2881 SlicedString* sliced = SlicedString::cast(string); | 2897 SlicedString* sliced = SlicedString::cast(string); |
| 2882 offset += sliced->start(); | 2898 offset += sliced->start(); |
| 2883 string = String::cast(sliced->buffer()); | 2899 string = String::cast(sliced->buffer()); |
| 2884 string_tag = string->representation_tag(); | 2900 string_tag = string->representation_tag(); |
| 2885 } else if (string_tag == kConsStringTag) { | 2901 } else if (string_tag == kConsStringTag) { |
| 2886 ConsString* cons = ConsString::cast(string); | 2902 ConsString* cons = ConsString::cast(string); |
| 2887 ASSERT(String::cast(cons->second())->length() == 0); | 2903 ASSERT(String::cast(cons->second())->length() == 0); |
| 2888 string = String::cast(cons->first()); | 2904 string = String::cast(cons->first()); |
| 2889 string_tag = string->representation_tag(); | 2905 string_tag = string->representation_tag(); |
| 2890 } | 2906 } |
| 2891 if (string_tag == kSeqStringTag) { | 2907 if (string_tag == kSeqStringTag) { |
| 2892 SeqAsciiString* seq = SeqAsciiString::cast(string); | 2908 SeqAsciiString* seq = SeqAsciiString::cast(string); |
| 2893 char* start = reinterpret_cast<char*>(seq->GetCharsAddress()); | 2909 byte* start = seq->GetCharsAddress(); |
| 2894 return Vector<const char>(start + offset, length); | 2910 return Vector<const byte>(start + offset, length); |
| 2895 } | 2911 } |
| 2896 ASSERT(string_tag == kExternalStringTag); | 2912 ASSERT(string_tag == kExternalStringTag); |
| 2897 ExternalAsciiString* ext = ExternalAsciiString::cast(string); | 2913 ExternalAsciiString* ext = ExternalAsciiString::cast(string); |
| 2898 const char* start = ext->resource()->data(); | 2914 const byte* start = reinterpret_cast<const byte*>(ext->resource()->data()); |
|
Christian Plesner Hansen
2008/10/21 14:16:22
Bleh. Why not stick with char?
Erik Corry
2008/10/22 11:59:48
Done
| |
| 2899 return Vector<const char>(start + offset, length); | 2915 return Vector<const byte>(start + offset, length); |
| 2900 } | 2916 } |
| 2901 | 2917 |
| 2902 | 2918 |
| 2903 Vector<const uc16> String::ToUC16Vector() { | 2919 Vector<const uc16> String::ToUC16Vector() { |
| 2904 ASSERT(IsTwoByteStringRepresentation()); | 2920 ASSERT(IsTwoByteStringRepresentation()); |
| 2905 ASSERT(IsFlat()); | 2921 ASSERT(IsFlat()); |
| 2906 | 2922 |
| 2907 int offset = 0; | 2923 int offset = 0; |
| 2908 int length = this->length(); | 2924 int length = this->length(); |
| 2909 StringRepresentationTag string_tag = representation_tag(); | 2925 StringRepresentationTag string_tag = representation_tag(); |
| (...skipping 640 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3550 String* buf = String::cast(buffer()); | 3566 String* buf = String::cast(buffer()); |
| 3551 ASSERT(!buf->StringIsSlicedString()); | 3567 ASSERT(!buf->StringIsSlicedString()); |
| 3552 if (buf->StringIsConsString()) { | 3568 if (buf->StringIsConsString()) { |
| 3553 Object* ok = buf->Flatten(); | 3569 Object* ok = buf->Flatten(); |
| 3554 if (ok->IsFailure()) return ok; | 3570 if (ok->IsFailure()) return ok; |
| 3555 } | 3571 } |
| 3556 return this; | 3572 return this; |
| 3557 } | 3573 } |
| 3558 | 3574 |
| 3559 | 3575 |
| 3560 void String::Flatten(String* src, | 3576 // Assumes that if the sink is ASCII then the src will also be ASCII |
| 3561 String* sink, | 3577 // representation (not just ASCII in a 16 bit string). |
| 3562 int f, | 3578 template <typename sinkchar> |
| 3563 int t, | 3579 void String::WriteToFlat(String* src, |
| 3564 int so) { | 3580 sinkchar* sink, |
| 3581 int f, | |
| 3582 int t) { | |
| 3565 String* source = src; | 3583 String* source = src; |
| 3566 int from = f; | 3584 int from = f; |
| 3567 int to = t; | 3585 int to = t; |
| 3568 int sink_offset = so; | |
| 3569 while (true) { | 3586 while (true) { |
| 3570 ASSERT(0 <= from && from <= to && to <= source->length()); | 3587 ASSERT(0 <= from && from <= to && to <= source->length()); |
| 3571 ASSERT(0 <= sink_offset && sink_offset < sink->length()); | 3588 switch (source->full_representation_tag()) { |
| 3572 switch (source->representation_tag()) { | 3589 case kAsciiStringTag + kExternalStringTag: { |
| 3573 case kSeqStringTag: | 3590 if (sizeof(sinkchar) == 1) { |
| 3574 case kExternalStringTag: { | 3591 memcpy( |
|
Christian Plesner Hansen
2008/10/21 14:16:22
Could this be simplified by using a template-ified
Erik Corry
2008/10/22 11:59:48
Done.
| |
| 3575 Access<StringInputBuffer> buffer(&string_input_buffer); | 3592 sink, |
| 3576 buffer->Reset(from, source); | 3593 ExternalAsciiString::cast(source)->resource()->data() + from, |
| 3577 int j = sink_offset; | 3594 to - from); |
| 3578 for (int i = from; i < to; i++) { | 3595 } else { |
| 3579 uc32 c = buffer->GetNext(); | 3596 Cpy168( |
| 3580 sink->Set(j++, c); | 3597 sink, |
| 3598 // Sign cast. | |
| 3599 reinterpret_cast<const byte*>( | |
| 3600 ExternalAsciiString::cast(source)->resource()->data()) + | |
| 3601 from, | |
| 3602 to - from); | |
| 3581 } | 3603 } |
| 3582 return; | 3604 return; |
| 3583 } | 3605 } |
| 3584 case kSlicedStringTag: { | 3606 case kTwoByteStringTag + kExternalStringTag: { |
|
Christian Plesner Hansen
2008/10/21 14:16:22
If | gives the same result as + we should use that
Erik Corry
2008/10/22 11:59:48
Done
| |
| 3607 ASSERT(sizeof(sinkchar) == 2); | |
| 3608 memcpy( | |
| 3609 sink, | |
| 3610 ExternalTwoByteString::cast(source)->resource()->data() + (from << 1 ), | |
| 3611 (to - from) << 1); | |
| 3612 return; | |
| 3613 } | |
| 3614 case kAsciiStringTag + kSeqStringTag: { | |
| 3615 if (sizeof(sinkchar) == 1) { | |
| 3616 const byte* src = | |
|
Christian Plesner Hansen
2008/10/21 14:16:22
Isn't this the branch where we can memcpy? Source
Erik Corry
2008/10/22 11:59:48
The non-memcpy may be marginally faster, but this
| |
| 3617 SeqAsciiString::cast(source)->GetCharsAddress() + from; | |
| 3618 const byte* end = src - from + to; | |
| 3619 while (src < end) { | |
| 3620 *sink++ = *src++; | |
| 3621 } | |
| 3622 } else { | |
| 3623 Cpy168( | |
|
Christian Plesner Hansen
2008/10/21 14:16:22
Conversely, this looks to me like we're memcpying
Erik Corry
2008/10/22 11:59:48
Gone in new version.
| |
| 3624 sink, | |
| 3625 SeqAsciiString::cast(source)->GetCharsAddress() + from, | |
| 3626 to - from); | |
| 3627 } | |
| 3628 return; | |
| 3629 } | |
| 3630 case kTwoByteStringTag + kSeqStringTag: { | |
| 3631 ASSERT(sizeof(sinkchar) == 2); | |
| 3632 memcpy( | |
| 3633 sink, | |
| 3634 SeqTwoByteString::cast(source)->GetCharsAddress() + (from << 1), | |
| 3635 (to - from) << 1); | |
| 3636 return; | |
| 3637 } | |
| 3638 case kAsciiStringTag + kSlicedStringTag: | |
| 3639 case kTwoByteStringTag + kSlicedStringTag: { | |
| 3585 SlicedString* sliced_string = SlicedString::cast(source); | 3640 SlicedString* sliced_string = SlicedString::cast(source); |
| 3586 int start = sliced_string->start(); | 3641 int start = sliced_string->start(); |
| 3587 from += start; | 3642 from += start; |
| 3588 to += start; | 3643 to += start; |
| 3589 source = String::cast(sliced_string->buffer()); | 3644 source = String::cast(sliced_string->buffer()); |
| 3645 break; | |
| 3590 } | 3646 } |
| 3591 break; | 3647 case kAsciiStringTag + kConsStringTag: |
| 3592 case kConsStringTag: { | 3648 case kTwoByteStringTag + kConsStringTag: { |
| 3593 ConsString* cons_string = ConsString::cast(source); | 3649 ConsString* cons_string = ConsString::cast(source); |
| 3594 String* first = String::cast(cons_string->first()); | 3650 String* first = String::cast(cons_string->first()); |
| 3595 int boundary = first->length(); | 3651 int boundary = first->length(); |
| 3596 if (to - boundary >= boundary - from) { | 3652 if (boundary < 64 || to - boundary >= boundary - from) { |
|
Christian Plesner Hansen
2008/10/21 14:16:22
Magic number. Please define a constant.
Erik Corry
2008/10/22 11:59:48
I got rid of this optimization because I found a t
| |
| 3597 // Right hand side is longer. Recurse over left. | 3653 // Right hand side is longer. Recurse over left. |
| 3598 if (from < boundary) { | 3654 if (from < boundary) { |
| 3599 Flatten(first, sink, from, boundary, sink_offset); | 3655 WriteToFlat(first, sink, from, boundary); |
| 3600 sink_offset += boundary - from; | 3656 sink += boundary - from; |
| 3601 from = 0; | 3657 from = 0; |
| 3602 } else { | 3658 } else { |
| 3603 from -= boundary; | 3659 from -= boundary; |
| 3604 } | 3660 } |
| 3605 to -= boundary; | 3661 to -= boundary; |
| 3606 source = String::cast(cons_string->second()); | 3662 source = String::cast(cons_string->second()); |
| 3607 } else { | 3663 } else { |
| 3608 // Left hand side is longer. Recurse over right. The hasher | 3664 // Left hand side is longer. Recurse over right. The hasher |
| 3609 // needs us to visit the string from left to right so doing | 3665 // needs us to visit the string from left to right so doing |
| 3610 // this invalidates that hash. | 3666 // this invalidates that hash. |
| 3611 if (to > boundary) { | 3667 if (to > boundary) { |
| 3612 String* second = String::cast(cons_string->second()); | 3668 String* second = String::cast(cons_string->second()); |
| 3613 Flatten(second, | 3669 WriteToFlat(second, |
| 3614 sink, | 3670 sink + boundary - from, |
| 3615 0, | 3671 0, |
| 3616 to - boundary, | 3672 to - boundary); |
| 3617 sink_offset + boundary - from); | |
| 3618 to = boundary; | 3673 to = boundary; |
| 3619 } | 3674 } |
| 3620 source = first; | 3675 source = first; |
| 3621 } | 3676 } |
| 3677 break; | |
| 3622 } | 3678 } |
| 3623 break; | |
| 3624 } | 3679 } |
| 3625 } | 3680 } |
| 3626 } | 3681 } |
| 3627 | 3682 |
| 3628 | 3683 |
| 3629 void SlicedString::SlicedStringIterateBody(ObjectVisitor* v) { | 3684 void SlicedString::SlicedStringIterateBody(ObjectVisitor* v) { |
| 3630 IteratePointer(v, kBufferOffset); | 3685 IteratePointer(v, kBufferOffset); |
| 3631 } | 3686 } |
| 3632 | 3687 |
| 3633 | 3688 |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3683 } | 3738 } |
| 3684 | 3739 |
| 3685 | 3740 |
| 3686 static StringInputBuffer string_compare_buffer_b; | 3741 static StringInputBuffer string_compare_buffer_b; |
| 3687 | 3742 |
| 3688 | 3743 |
| 3689 template <typename IteratorA> | 3744 template <typename IteratorA> |
| 3690 static inline bool CompareStringContentsPartial(IteratorA* ia, String* b) { | 3745 static inline bool CompareStringContentsPartial(IteratorA* ia, String* b) { |
| 3691 if (b->IsFlat()) { | 3746 if (b->IsFlat()) { |
| 3692 if (b->IsAsciiRepresentation()) { | 3747 if (b->IsAsciiRepresentation()) { |
| 3693 VectorIterator<char> ib(b->ToAsciiVector()); | 3748 VectorIterator<const byte> ib(b->ToAsciiVector()); |
|
Christian Plesner Hansen
2008/10/21 14:16:22
There's no need to explicitly add 'const' to a Vec
Erik Corry
2008/10/22 11:59:48
OK
| |
| 3694 return CompareStringContents(ia, &ib); | 3749 return CompareStringContents(ia, &ib); |
| 3695 } else { | 3750 } else { |
| 3696 VectorIterator<uc16> ib(b->ToUC16Vector()); | 3751 VectorIterator<const uc16> ib(b->ToUC16Vector()); |
| 3697 return CompareStringContents(ia, &ib); | 3752 return CompareStringContents(ia, &ib); |
| 3698 } | 3753 } |
| 3699 } else { | 3754 } else { |
| 3700 string_compare_buffer_b.Reset(0, b); | 3755 string_compare_buffer_b.Reset(0, b); |
| 3701 return CompareStringContents(ia, &string_compare_buffer_b); | 3756 return CompareStringContents(ia, &string_compare_buffer_b); |
| 3702 } | 3757 } |
| 3703 } | 3758 } |
| 3704 | 3759 |
| 3705 | 3760 |
| 3706 static StringInputBuffer string_compare_buffer_a; | 3761 static StringInputBuffer string_compare_buffer_a; |
| (...skipping 13 matching lines...) Expand all Loading... | |
| 3720 | 3775 |
| 3721 if (this->IsSeqAsciiString() && other->IsSeqAsciiString()) { | 3776 if (this->IsSeqAsciiString() && other->IsSeqAsciiString()) { |
| 3722 const char* str1 = SeqAsciiString::cast(this)->GetChars(); | 3777 const char* str1 = SeqAsciiString::cast(this)->GetChars(); |
| 3723 const char* str2 = SeqAsciiString::cast(other)->GetChars(); | 3778 const char* str2 = SeqAsciiString::cast(other)->GetChars(); |
| 3724 return CompareRawStringContents(Vector<const char>(str1, len), | 3779 return CompareRawStringContents(Vector<const char>(str1, len), |
| 3725 Vector<const char>(str2, len)); | 3780 Vector<const char>(str2, len)); |
| 3726 } | 3781 } |
| 3727 | 3782 |
| 3728 if (this->IsFlat()) { | 3783 if (this->IsFlat()) { |
| 3729 if (this->IsAsciiRepresentation()) { | 3784 if (this->IsAsciiRepresentation()) { |
| 3730 Vector<const char> vec1 = this->ToAsciiVector(); | 3785 Vector<const byte> vec1 = this->ToAsciiVector(); |
| 3731 if (other->IsFlat()) { | 3786 if (other->IsFlat()) { |
| 3732 if (other->IsAsciiRepresentation()) { | 3787 if (other->IsAsciiRepresentation()) { |
| 3733 Vector<const char> vec2 = other->ToAsciiVector(); | 3788 Vector<const byte> vec2 = other->ToAsciiVector(); |
| 3734 return CompareRawStringContents(vec1, vec2); | 3789 return CompareRawStringContents(vec1, vec2); |
| 3735 } else { | 3790 } else { |
| 3736 VectorIterator<char> buf1(vec1); | 3791 VectorIterator<const byte> buf1(vec1); |
| 3737 VectorIterator<uc16> ib(other->ToUC16Vector()); | 3792 VectorIterator<const uc16> ib(other->ToUC16Vector()); |
| 3738 return CompareStringContents(&buf1, &ib); | 3793 return CompareStringContents(&buf1, &ib); |
| 3739 } | 3794 } |
| 3740 } else { | 3795 } else { |
| 3741 VectorIterator<char> buf1(vec1); | 3796 VectorIterator<const byte> buf1(vec1); |
| 3742 string_compare_buffer_b.Reset(0, other); | 3797 string_compare_buffer_b.Reset(0, other); |
| 3743 return CompareStringContents(&buf1, &string_compare_buffer_b); | 3798 return CompareStringContents(&buf1, &string_compare_buffer_b); |
| 3744 } | 3799 } |
| 3745 } else { | 3800 } else { |
| 3746 Vector<const uc16> vec1 = this->ToUC16Vector(); | 3801 Vector<const uc16> vec1 = this->ToUC16Vector(); |
| 3747 if (other->IsFlat()) { | 3802 if (other->IsFlat()) { |
| 3748 if (other->IsAsciiRepresentation()) { | 3803 if (other->IsAsciiRepresentation()) { |
| 3749 VectorIterator<uc16> buf1(vec1); | 3804 VectorIterator<const uc16> buf1(vec1); |
| 3750 VectorIterator<char> ib(other->ToAsciiVector()); | 3805 VectorIterator<const byte> ib(other->ToAsciiVector()); |
| 3751 return CompareStringContents(&buf1, &ib); | 3806 return CompareStringContents(&buf1, &ib); |
| 3752 } else { | 3807 } else { |
| 3753 Vector<const uc16> vec2(other->ToUC16Vector()); | 3808 Vector<const uc16> vec2(other->ToUC16Vector()); |
| 3754 return CompareRawStringContents(vec1, vec2); | 3809 return CompareRawStringContents(vec1, vec2); |
| 3755 } | 3810 } |
| 3756 } else { | 3811 } else { |
| 3757 VectorIterator<uc16> buf1(vec1); | 3812 VectorIterator<const uc16> buf1(vec1); |
| 3758 string_compare_buffer_b.Reset(0, other); | 3813 string_compare_buffer_b.Reset(0, other); |
| 3759 return CompareStringContents(&buf1, &string_compare_buffer_b); | 3814 return CompareStringContents(&buf1, &string_compare_buffer_b); |
| 3760 } | 3815 } |
| 3761 } | 3816 } |
| 3762 } else { | 3817 } else { |
| 3763 string_compare_buffer_a.Reset(0, this); | 3818 string_compare_buffer_a.Reset(0, this); |
| 3764 return CompareStringContentsPartial(&string_compare_buffer_a, other); | 3819 return CompareStringContentsPartial(&string_compare_buffer_a, other); |
| 3765 } | 3820 } |
| 3766 } | 3821 } |
| 3767 | 3822 |
| (...skipping 2710 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 6478 // No break point. | 6533 // No break point. |
| 6479 if (break_point_objects()->IsUndefined()) return 0; | 6534 if (break_point_objects()->IsUndefined()) return 0; |
| 6480 // Single beak point. | 6535 // Single beak point. |
| 6481 if (!break_point_objects()->IsFixedArray()) return 1; | 6536 if (!break_point_objects()->IsFixedArray()) return 1; |
| 6482 // Multiple break points. | 6537 // Multiple break points. |
| 6483 return FixedArray::cast(break_point_objects())->length(); | 6538 return FixedArray::cast(break_point_objects())->length(); |
| 6484 } | 6539 } |
| 6485 | 6540 |
| 6486 | 6541 |
| 6487 } } // namespace v8::internal | 6542 } } // namespace v8::internal |
| OLD | NEW |