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 1776 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1787 // If we still have the original map, set in-object properties directly. | 1787 // If we still have the original map, set in-object properties directly. |
1788 regexp->InObjectPropertyAtPut(JSRegExp::kSourceFieldIndex, source); | 1788 regexp->InObjectPropertyAtPut(JSRegExp::kSourceFieldIndex, source); |
1789 // Both true and false are immovable immortal objects so no need for write | 1789 // Both true and false are immovable immortal objects so no need for write |
1790 // barrier. | 1790 // barrier. |
1791 regexp->InObjectPropertyAtPut( | 1791 regexp->InObjectPropertyAtPut( |
1792 JSRegExp::kGlobalFieldIndex, global, SKIP_WRITE_BARRIER); | 1792 JSRegExp::kGlobalFieldIndex, global, SKIP_WRITE_BARRIER); |
1793 regexp->InObjectPropertyAtPut( | 1793 regexp->InObjectPropertyAtPut( |
1794 JSRegExp::kIgnoreCaseFieldIndex, ignoreCase, SKIP_WRITE_BARRIER); | 1794 JSRegExp::kIgnoreCaseFieldIndex, ignoreCase, SKIP_WRITE_BARRIER); |
1795 regexp->InObjectPropertyAtPut( | 1795 regexp->InObjectPropertyAtPut( |
1796 JSRegExp::kMultilineFieldIndex, multiline, SKIP_WRITE_BARRIER); | 1796 JSRegExp::kMultilineFieldIndex, multiline, SKIP_WRITE_BARRIER); |
1797 regexp->ResetLastIndex(); | 1797 regexp->InObjectPropertyAtPut( |
| 1798 JSRegExp::kLastIndexFieldIndex, Smi::FromInt(0), SKIP_WRITE_BARRIER); |
1798 return regexp; | 1799 return regexp; |
1799 } | 1800 } |
1800 | 1801 |
1801 // Map has changed, so use generic, but slower, method. | 1802 // Map has changed, so use generic, but slower, method. |
1802 PropertyAttributes final = | 1803 PropertyAttributes final = |
1803 static_cast<PropertyAttributes>(READ_ONLY | DONT_ENUM | DONT_DELETE); | 1804 static_cast<PropertyAttributes>(READ_ONLY | DONT_ENUM | DONT_DELETE); |
1804 PropertyAttributes writable = | 1805 PropertyAttributes writable = |
1805 static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE); | 1806 static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE); |
1806 Heap* heap = isolate->heap(); | 1807 Heap* heap = isolate->heap(); |
1807 MaybeObject* result; | 1808 MaybeObject* result; |
(...skipping 1096 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2904 String::cast(pattern_regexp->DataAt(JSRegExp::kAtomPatternIndex)); | 2905 String::cast(pattern_regexp->DataAt(JSRegExp::kAtomPatternIndex)); |
2905 int subject_len = subject->length(); | 2906 int subject_len = subject->length(); |
2906 int pattern_len = pattern->length(); | 2907 int pattern_len = pattern->length(); |
2907 int replacement_len = replacement->length(); | 2908 int replacement_len = replacement->length(); |
2908 | 2909 |
2909 FindStringIndicesDispatch( | 2910 FindStringIndicesDispatch( |
2910 isolate, *subject, pattern, &indices, 0xffffffff, zone); | 2911 isolate, *subject, pattern, &indices, 0xffffffff, zone); |
2911 | 2912 |
2912 int matches = indices.length(); | 2913 int matches = indices.length(); |
2913 if (matches == 0) { | 2914 if (matches == 0) { |
2914 pattern_regexp->ResetLastIndex(); | 2915 JSRegExp::ResetLastIndex(isolate, pattern_regexp); |
2915 return *subject; | 2916 return *subject; |
2916 } | 2917 } |
2917 | 2918 |
2918 // Detect integer overflow. | 2919 // Detect integer overflow. |
2919 int64_t result_len_64 = | 2920 int64_t result_len_64 = |
2920 (static_cast<int64_t>(replacement_len) - | 2921 (static_cast<int64_t>(replacement_len) - |
2921 static_cast<int64_t>(pattern_len)) * | 2922 static_cast<int64_t>(pattern_len)) * |
2922 static_cast<int64_t>(matches) + | 2923 static_cast<int64_t>(matches) + |
2923 static_cast<int64_t>(subject_len); | 2924 static_cast<int64_t>(subject_len); |
2924 if (result_len_64 > INT_MAX) return Failure::OutOfMemoryException(0x11); | 2925 if (result_len_64 > INT_MAX) return Failure::OutOfMemoryException(0x11); |
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3007 isolate, subject, regexp, replacement, last_match_info); | 3008 isolate, subject, regexp, replacement, last_match_info); |
3008 } | 3009 } |
3009 } | 3010 } |
3010 | 3011 |
3011 RegExpImpl::GlobalCache global_cache(regexp, subject, is_global, isolate); | 3012 RegExpImpl::GlobalCache global_cache(regexp, subject, is_global, isolate); |
3012 if (global_cache.HasException()) return Failure::Exception(); | 3013 if (global_cache.HasException()) return Failure::Exception(); |
3013 | 3014 |
3014 int32_t* current_match = global_cache.FetchNext(); | 3015 int32_t* current_match = global_cache.FetchNext(); |
3015 if (current_match == NULL) { | 3016 if (current_match == NULL) { |
3016 if (global_cache.HasException()) return Failure::Exception(); | 3017 if (global_cache.HasException()) return Failure::Exception(); |
3017 regexp->ResetLastIndex(); | 3018 JSRegExp::ResetLastIndex(isolate, regexp); |
3018 return *subject; | 3019 return *subject; |
3019 } | 3020 } |
3020 | 3021 |
3021 // Guessing the number of parts that the final result string is built | 3022 // Guessing the number of parts that the final result string is built |
3022 // from. Global regexps can match any number of times, so we guess | 3023 // from. Global regexps can match any number of times, so we guess |
3023 // conservatively. | 3024 // conservatively. |
3024 int expected_parts = | 3025 int expected_parts = |
3025 (compiled_replacement.parts() + 1) * (is_global ? 4 : 1) + 1; | 3026 (compiled_replacement.parts() + 1) * (is_global ? 4 : 1) + 1; |
3026 ReplacementStringBuilder builder(isolate->heap(), | 3027 ReplacementStringBuilder builder(isolate->heap(), |
3027 subject, | 3028 subject, |
(...skipping 78 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3106 last_match_info); | 3107 last_match_info); |
3107 } | 3108 } |
3108 } | 3109 } |
3109 | 3110 |
3110 RegExpImpl::GlobalCache global_cache(regexp, subject, is_global, isolate); | 3111 RegExpImpl::GlobalCache global_cache(regexp, subject, is_global, isolate); |
3111 if (global_cache.HasException()) return Failure::Exception(); | 3112 if (global_cache.HasException()) return Failure::Exception(); |
3112 | 3113 |
3113 int32_t* current_match = global_cache.FetchNext(); | 3114 int32_t* current_match = global_cache.FetchNext(); |
3114 if (current_match == NULL) { | 3115 if (current_match == NULL) { |
3115 if (global_cache.HasException()) return Failure::Exception(); | 3116 if (global_cache.HasException()) return Failure::Exception(); |
3116 regexp->ResetLastIndex(); | 3117 JSRegExp::ResetLastIndex(isolate, regexp); |
3117 return *subject; | 3118 return *subject; |
3118 } | 3119 } |
3119 | 3120 |
3120 int start = current_match[0]; | 3121 int start = current_match[0]; |
3121 int end = current_match[1]; | 3122 int end = current_match[1]; |
3122 int capture_count = regexp->CaptureCount(); | 3123 int capture_count = regexp->CaptureCount(); |
3123 int subject_length = subject->length(); | 3124 int subject_length = subject->length(); |
3124 | 3125 |
3125 int new_length = subject_length - (end - start); | 3126 int new_length = subject_length - (end - start); |
3126 if (new_length == 0) return isolate->heap()->empty_string(); | 3127 if (new_length == 0) return isolate->heap()->empty_string(); |
(...skipping 10392 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
13519 // Handle last resort GC and make sure to allow future allocations | 13520 // Handle last resort GC and make sure to allow future allocations |
13520 // to grow the heap without causing GCs (if possible). | 13521 // to grow the heap without causing GCs (if possible). |
13521 isolate->counters()->gc_last_resort_from_js()->Increment(); | 13522 isolate->counters()->gc_last_resort_from_js()->Increment(); |
13522 isolate->heap()->CollectAllGarbage(Heap::kNoGCFlags, | 13523 isolate->heap()->CollectAllGarbage(Heap::kNoGCFlags, |
13523 "Runtime::PerformGC"); | 13524 "Runtime::PerformGC"); |
13524 } | 13525 } |
13525 } | 13526 } |
13526 | 13527 |
13527 | 13528 |
13528 } } // namespace v8::internal | 13529 } } // namespace v8::internal |
OLD | NEW |