| Index: src/compiler/js-builtin-reducer.cc
|
| diff --git a/src/compiler/js-builtin-reducer.cc b/src/compiler/js-builtin-reducer.cc
|
| index 762020438878fdbc5566ba07848fd601c870b6ca..78c3286d059e3d2bf26d98cc8c44121e18230615 100644
|
| --- a/src/compiler/js-builtin-reducer.cc
|
| +++ b/src/compiler/js-builtin-reducer.cc
|
| @@ -1026,6 +1026,139 @@ Reduction JSBuiltinReducer::ReduceStringCharCodeAt(Node* node) {
|
| return NoChange();
|
| }
|
|
|
| +Reduction JSBuiltinReducer::ReduceStringIteratorNext(Node* node) {
|
| + Node* receiver = NodeProperties::GetValueInput(node, 1);
|
| + Node* effect = NodeProperties::GetEffectInput(node);
|
| + Node* control = NodeProperties::GetControlInput(node);
|
| + Node* context = NodeProperties::GetContextInput(node);
|
| + if (HasInstanceTypeWitness(receiver, effect, JS_STRING_ITERATOR_TYPE)) {
|
| + Node* string = effect = graph()->NewNode(
|
| + simplified()->LoadField(AccessBuilder::ForJSStringIteratorString()),
|
| + receiver, effect, control);
|
| + Node* index = effect = graph()->NewNode(
|
| + simplified()->LoadField(AccessBuilder::ForJSStringIteratorIndex()),
|
| + receiver, effect, control);
|
| + Node* length = effect = graph()->NewNode(
|
| + simplified()->LoadField(AccessBuilder::ForStringLength()), string,
|
| + effect, control);
|
| +
|
| + // branch0: if (index < length)
|
| + Node* check0 =
|
| + graph()->NewNode(simplified()->NumberLessThan(), index, length);
|
| + Node* branch0 =
|
| + graph()->NewNode(common()->Branch(BranchHint::kTrue), check0, control);
|
| +
|
| + Node* etrue0 = effect;
|
| + Node* if_true0 = graph()->NewNode(common()->IfTrue(), branch0);
|
| + Node* done_true;
|
| + Node* vtrue0;
|
| + {
|
| + done_true = jsgraph()->FalseConstant();
|
| + Node* lead = graph()->NewNode(simplified()->StringCharCodeAt(), string,
|
| + index, if_true0);
|
| +
|
| + // branch1: if ((lead & 0xFC00) === 0xD800)
|
| + Node* check1 = graph()->NewNode(
|
| + simplified()->NumberEqual(),
|
| + graph()->NewNode(simplified()->NumberBitwiseAnd(), lead,
|
| + jsgraph()->Int32Constant(0xFC00)),
|
| + jsgraph()->Int32Constant(0xD800));
|
| + Node* branch1 = graph()->NewNode(common()->Branch(BranchHint::kFalse),
|
| + check1, if_true0);
|
| + Node* if_true1 = graph()->NewNode(common()->IfTrue(), branch1);
|
| + Node* vtrue1;
|
| + {
|
| + Node* next_index = graph()->NewNode(simplified()->NumberAdd(), index,
|
| + jsgraph()->OneConstant());
|
| + // branch2: if ((index + 1) < length)
|
| + Node* check2 = graph()->NewNode(simplified()->NumberLessThan(),
|
| + next_index, length);
|
| + Node* branch2 = graph()->NewNode(common()->Branch(BranchHint::kTrue),
|
| + check2, if_true1);
|
| + Node* if_true2 = graph()->NewNode(common()->IfTrue(), branch2);
|
| + Node* vtrue2;
|
| + {
|
| + Node* trail = graph()->NewNode(simplified()->StringCharCodeAt(),
|
| + string, next_index, if_true2);
|
| + // branch3: if ((trail & 0xFC00) === 0xDC00)
|
| + Node* check3 = graph()->NewNode(
|
| + simplified()->NumberEqual(),
|
| + graph()->NewNode(simplified()->NumberBitwiseAnd(), trail,
|
| + jsgraph()->Int32Constant(0xFC00)),
|
| + jsgraph()->Int32Constant(0xDC00));
|
| + Node* branch3 = graph()->NewNode(common()->Branch(BranchHint::kTrue),
|
| + check3, if_true2);
|
| + Node* if_true3 = graph()->NewNode(common()->IfTrue(), branch3);
|
| + Node* vtrue3;
|
| + {
|
| + vtrue3 = graph()->NewNode(
|
| + simplified()->NumberBitwiseOr(),
|
| + graph()->NewNode(simplified()->NumberShiftLeft(), trail,
|
| + jsgraph()->Int32Constant(16)),
|
| + lead);
|
| + }
|
| +
|
| + Node* if_false3 = graph()->NewNode(common()->IfFalse(), branch3);
|
| + Node* vfalse3 = lead;
|
| + if_true2 = graph()->NewNode(common()->Merge(2), if_true3, if_false3);
|
| + vtrue2 =
|
| + graph()->NewNode(common()->Phi(MachineRepresentation::kWord32, 2),
|
| + vtrue3, vfalse3, if_true2);
|
| + }
|
| +
|
| + Node* if_false2 = graph()->NewNode(common()->IfFalse(), branch2);
|
| + Node* vfalse2 = lead;
|
| + if_true1 = graph()->NewNode(common()->Merge(2), if_true2, if_false2);
|
| + vtrue1 =
|
| + graph()->NewNode(common()->Phi(MachineRepresentation::kWord32, 2),
|
| + vtrue2, vfalse2, if_true1);
|
| + }
|
| +
|
| + Node* if_false1 = graph()->NewNode(common()->IfFalse(), branch1);
|
| + Node* vfalse1 = lead;
|
| + if_true0 = graph()->NewNode(common()->Merge(2), if_true1, if_false1);
|
| + vtrue0 =
|
| + graph()->NewNode(common()->Phi(MachineRepresentation::kWord32, 2),
|
| + vtrue1, vfalse1, if_true0);
|
| + vtrue0 = graph()->NewNode(
|
| + simplified()->StringFromCodePoint(UnicodeEncoding::UTF16), vtrue0);
|
| +
|
| + // Update iterator.[[NextIndex]]
|
| + Node* char_length = etrue0 = graph()->NewNode(
|
| + simplified()->LoadField(AccessBuilder::ForStringLength()), vtrue0,
|
| + etrue0, if_true0);
|
| + index = graph()->NewNode(simplified()->NumberAdd(), index, char_length);
|
| + etrue0 = graph()->NewNode(
|
| + simplified()->StoreField(AccessBuilder::ForJSStringIteratorIndex()),
|
| + receiver, index, etrue0, if_true0);
|
| + }
|
| +
|
| + Node* if_false0 = graph()->NewNode(common()->IfFalse(), branch0);
|
| + Node* done_false;
|
| + Node* vfalse0;
|
| + {
|
| + vfalse0 = jsgraph()->UndefinedConstant();
|
| + done_false = jsgraph()->TrueConstant();
|
| + }
|
| +
|
| + control = graph()->NewNode(common()->Merge(2), if_true0, if_false0);
|
| + effect = graph()->NewNode(common()->EffectPhi(2), etrue0, effect, control);
|
| + Node* value =
|
| + graph()->NewNode(common()->Phi(MachineRepresentation::kTagged, 2),
|
| + vtrue0, vfalse0, control);
|
| + Node* done =
|
| + graph()->NewNode(common()->Phi(MachineRepresentation::kTagged, 2),
|
| + done_true, done_false, control);
|
| +
|
| + value = effect = graph()->NewNode(javascript()->CreateIterResultObject(),
|
| + value, done, context, effect);
|
| +
|
| + ReplaceWithValue(node, value, effect, control);
|
| + return Replace(value);
|
| + }
|
| + return NoChange();
|
| +}
|
| +
|
| Reduction JSBuiltinReducer::ReduceArrayBufferViewAccessor(
|
| Node* node, InstanceType instance_type, FieldAccess const& access) {
|
| Node* receiver = NodeProperties::GetValueInput(node, 1);
|
| @@ -1195,6 +1328,8 @@ Reduction JSBuiltinReducer::Reduce(Node* node) {
|
| return ReduceStringCharAt(node);
|
| case kStringCharCodeAt:
|
| return ReduceStringCharCodeAt(node);
|
| + case kStringIteratorNext:
|
| + return ReduceStringIteratorNext(node);
|
| case kDataViewByteLength:
|
| return ReduceArrayBufferViewAccessor(
|
| node, JS_DATA_VIEW_TYPE,
|
| @@ -1254,6 +1389,10 @@ SimplifiedOperatorBuilder* JSBuiltinReducer::simplified() const {
|
| return jsgraph()->simplified();
|
| }
|
|
|
| +JSOperatorBuilder* JSBuiltinReducer::javascript() const {
|
| + return jsgraph()->javascript();
|
| +}
|
| +
|
| } // namespace compiler
|
| } // namespace internal
|
| } // namespace v8
|
|
|