OLD | NEW |
1 // Copyright 2016 the V8 project authors. All rights reserved. | 1 // Copyright 2016 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/builtins/builtins-regexp.h" | 5 #include "src/builtins/builtins-regexp.h" |
6 #include "src/builtins/builtins-utils.h" | 6 #include "src/builtins/builtins-utils.h" |
7 #include "src/builtins/builtins.h" | 7 #include "src/builtins/builtins.h" |
8 #include "src/code-factory.h" | 8 #include "src/code-factory.h" |
9 #include "src/code-stub-assembler.h" | 9 #include "src/code-stub-assembler.h" |
10 #include "src/regexp/regexp-utils.h" | 10 #include "src/regexp/regexp-utils.h" |
(...skipping 1097 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1108 Node* const initial_map = | 1108 Node* const initial_map = |
1109 LoadObjectField(string_fun, JSFunction::kPrototypeOrInitialMapOffset); | 1109 LoadObjectField(string_fun, JSFunction::kPrototypeOrInitialMapOffset); |
1110 Node* const proto_map = LoadMap(LoadMapPrototype(initial_map)); | 1110 Node* const proto_map = LoadMap(LoadMapPrototype(initial_map)); |
1111 | 1111 |
1112 Branch(WordEqual(proto_map, initial_proto_initial_map), &out, &next); | 1112 Branch(WordEqual(proto_map, initial_proto_initial_map), &out, &next); |
1113 | 1113 |
1114 Bind(&next); | 1114 Bind(&next); |
1115 } | 1115 } |
1116 | 1116 |
1117 // Take the fast path for RegExps. | 1117 // Take the fast path for RegExps. |
1118 if (regexp_call != nullptr) { | 1118 { |
1119 Label stub_call(this), slow_lookup(this); | 1119 Label stub_call(this), slow_lookup(this); |
1120 | 1120 |
1121 RegExpBuiltinsAssembler regexp_asm(state()); | 1121 RegExpBuiltinsAssembler regexp_asm(state()); |
1122 regexp_asm.BranchIfFastRegExp(context, object_map, &stub_call, | 1122 regexp_asm.BranchIfFastRegExp(context, object_map, &stub_call, |
1123 &slow_lookup); | 1123 &slow_lookup); |
1124 | 1124 |
1125 Bind(&stub_call); | 1125 Bind(&stub_call); |
1126 Return(regexp_call()); | 1126 Return(regexp_call()); |
1127 | 1127 |
1128 Bind(&slow_lookup); | 1128 Bind(&slow_lookup); |
(...skipping 24 matching lines...) Expand all Loading... |
1153 Node* const receiver = Parameter(0); | 1153 Node* const receiver = Parameter(0); |
1154 Node* const search = Parameter(1); | 1154 Node* const search = Parameter(1); |
1155 Node* const replace = Parameter(2); | 1155 Node* const replace = Parameter(2); |
1156 Node* const context = Parameter(5); | 1156 Node* const context = Parameter(5); |
1157 | 1157 |
1158 Node* const smi_zero = SmiConstant(0); | 1158 Node* const smi_zero = SmiConstant(0); |
1159 | 1159 |
1160 RequireObjectCoercible(context, receiver, "String.prototype.replace"); | 1160 RequireObjectCoercible(context, receiver, "String.prototype.replace"); |
1161 | 1161 |
1162 // Redirect to replacer method if {search[@@replace]} is not undefined. | 1162 // Redirect to replacer method if {search[@@replace]} is not undefined. |
1163 // TODO(jgruber): Call RegExp.p.replace stub for fast path. | |
1164 | 1163 |
1165 MaybeCallFunctionAtSymbol( | 1164 MaybeCallFunctionAtSymbol( |
1166 context, search, isolate()->factory()->replace_symbol(), nullptr, | 1165 context, search, isolate()->factory()->replace_symbol(), |
| 1166 [=]() { |
| 1167 Callable tostring_callable = CodeFactory::ToString(isolate()); |
| 1168 Node* const subject_string = |
| 1169 CallStub(tostring_callable, context, receiver); |
| 1170 |
| 1171 Callable replace_callable = CodeFactory::RegExpReplace(isolate()); |
| 1172 return CallStub(replace_callable, context, search, subject_string, |
| 1173 replace); |
| 1174 }, |
1167 [=](Node* fn) { | 1175 [=](Node* fn) { |
1168 Callable call_callable = CodeFactory::Call(isolate()); | 1176 Callable call_callable = CodeFactory::Call(isolate()); |
1169 return CallJS(call_callable, context, fn, search, receiver, replace); | 1177 return CallJS(call_callable, context, fn, search, receiver, replace); |
1170 }); | 1178 }); |
1171 | 1179 |
1172 // Convert {receiver} and {search} to strings. | 1180 // Convert {receiver} and {search} to strings. |
1173 | 1181 |
1174 Callable tostring_callable = CodeFactory::ToString(isolate()); | 1182 Callable tostring_callable = CodeFactory::ToString(isolate()); |
1175 Node* const subject_string = CallStub(tostring_callable, context, receiver); | 1183 Node* const subject_string = CallStub(tostring_callable, context, receiver); |
1176 Node* const search_string = CallStub(tostring_callable, context, search); | 1184 Node* const search_string = CallStub(tostring_callable, context, search); |
(...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1310 Node* const receiver = Parameter(0); | 1318 Node* const receiver = Parameter(0); |
1311 Node* const separator = Parameter(1); | 1319 Node* const separator = Parameter(1); |
1312 Node* const limit = Parameter(2); | 1320 Node* const limit = Parameter(2); |
1313 Node* const context = Parameter(5); | 1321 Node* const context = Parameter(5); |
1314 | 1322 |
1315 Node* const smi_zero = SmiConstant(0); | 1323 Node* const smi_zero = SmiConstant(0); |
1316 | 1324 |
1317 RequireObjectCoercible(context, receiver, "String.prototype.split"); | 1325 RequireObjectCoercible(context, receiver, "String.prototype.split"); |
1318 | 1326 |
1319 // Redirect to splitter method if {separator[@@split]} is not undefined. | 1327 // Redirect to splitter method if {separator[@@split]} is not undefined. |
1320 // TODO(jgruber): Call RegExp.p.split stub for fast path. | |
1321 | 1328 |
1322 MaybeCallFunctionAtSymbol( | 1329 MaybeCallFunctionAtSymbol( |
1323 context, separator, isolate()->factory()->split_symbol(), nullptr, | 1330 context, separator, isolate()->factory()->split_symbol(), |
| 1331 [=]() { |
| 1332 Callable tostring_callable = CodeFactory::ToString(isolate()); |
| 1333 Node* const subject_string = |
| 1334 CallStub(tostring_callable, context, receiver); |
| 1335 |
| 1336 Callable split_callable = CodeFactory::RegExpSplit(isolate()); |
| 1337 return CallStub(split_callable, context, separator, subject_string, |
| 1338 limit); |
| 1339 }, |
1324 [=](Node* fn) { | 1340 [=](Node* fn) { |
1325 Callable call_callable = CodeFactory::Call(isolate()); | 1341 Callable call_callable = CodeFactory::Call(isolate()); |
1326 return CallJS(call_callable, context, fn, separator, receiver, limit); | 1342 return CallJS(call_callable, context, fn, separator, receiver, limit); |
1327 }); | 1343 }); |
1328 | 1344 |
1329 // String and integer conversions. | 1345 // String and integer conversions. |
1330 // TODO(jgruber): The old implementation used Uint32Max instead of SmiMax - | 1346 // TODO(jgruber): The old implementation used Uint32Max instead of SmiMax - |
1331 // but AFAIK there should not be a difference since arrays are capped at Smi | 1347 // but AFAIK there should not be a difference since arrays are capped at Smi |
1332 // lengths. | 1348 // lengths. |
1333 | 1349 |
(...skipping 521 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1855 CallRuntime(Runtime::kThrowIncompatibleMethodReceiver, context, | 1871 CallRuntime(Runtime::kThrowIncompatibleMethodReceiver, context, |
1856 HeapConstant(factory()->NewStringFromAsciiChecked( | 1872 HeapConstant(factory()->NewStringFromAsciiChecked( |
1857 "String Iterator.prototype.next", TENURED)), | 1873 "String Iterator.prototype.next", TENURED)), |
1858 iterator); | 1874 iterator); |
1859 Return(result); // Never reached. | 1875 Return(result); // Never reached. |
1860 } | 1876 } |
1861 } | 1877 } |
1862 | 1878 |
1863 } // namespace internal | 1879 } // namespace internal |
1864 } // namespace v8 | 1880 } // namespace v8 |
OLD | NEW |