| Index: src/compiler/js-typed-lowering.cc
|
| diff --git a/src/compiler/js-typed-lowering.cc b/src/compiler/js-typed-lowering.cc
|
| index 2338866d6d2274830dff5b132128ca3f9216659b..d9a627a1cf6a299b70636199f42c5a0ce4402fad 100644
|
| --- a/src/compiler/js-typed-lowering.cc
|
| +++ b/src/compiler/js-typed-lowering.cc
|
| @@ -490,124 +490,34 @@ Reduction JSTypedLowering::ReduceJSStrictEqual(Node* node, bool invert) {
|
| }
|
|
|
|
|
| -Reduction JSTypedLowering::ReduceJSToBooleanInput(Node* input) {
|
| - if (input->opcode() == IrOpcode::kJSToBoolean) {
|
| - // Recursively try to reduce the input first.
|
| - Reduction result = ReduceJSToBoolean(input);
|
| - if (result.Changed()) return result;
|
| - return Changed(input); // JSToBoolean(JSToBoolean(x)) => JSToBoolean(x)
|
| - }
|
| - // Check if we have a cached conversion.
|
| - Node* conversion = FindConversion<IrOpcode::kJSToBoolean>(input);
|
| - if (conversion) return Replace(conversion);
|
| +Reduction JSTypedLowering::ReduceJSUnaryNot(Node* node) {
|
| + Node* input = node->InputAt(0);
|
| Type* input_type = NodeProperties::GetBounds(input).upper;
|
| if (input_type->Is(Type::Boolean())) {
|
| - return Changed(input); // JSToBoolean(x:boolean) => x
|
| - }
|
| - if (input_type->Is(Type::Undefined())) {
|
| - // JSToBoolean(undefined) => #false
|
| - return Replace(jsgraph()->FalseConstant());
|
| - }
|
| - if (input_type->Is(Type::Null())) {
|
| - // JSToBoolean(null) => #false
|
| - return Replace(jsgraph()->FalseConstant());
|
| - }
|
| - if (input_type->Is(Type::DetectableReceiver())) {
|
| - // JSToBoolean(x:detectable) => #true
|
| - return Replace(jsgraph()->TrueConstant());
|
| - }
|
| - if (input_type->Is(Type::Undetectable())) {
|
| - // JSToBoolean(x:undetectable) => #false
|
| - return Replace(jsgraph()->FalseConstant());
|
| - }
|
| - if (input_type->Is(Type::OrderedNumber())) {
|
| - // JSToBoolean(x:ordered-number) => BooleanNot(NumberEqual(x, #0))
|
| - Node* cmp = graph()->NewNode(simplified()->NumberEqual(), input,
|
| - jsgraph()->ZeroConstant());
|
| - Node* inv = graph()->NewNode(simplified()->BooleanNot(), cmp);
|
| - return Replace(inv);
|
| - }
|
| - if (input_type->Is(Type::String())) {
|
| - // JSToBoolean(x:string) => BooleanNot(NumberEqual(x.length, #0))
|
| - FieldAccess access = AccessBuilder::ForStringLength();
|
| - Node* length = graph()->NewNode(simplified()->LoadField(access), input,
|
| - graph()->start(), graph()->start());
|
| - Node* cmp = graph()->NewNode(simplified()->NumberEqual(), length,
|
| - jsgraph()->ZeroConstant());
|
| - Node* inv = graph()->NewNode(simplified()->BooleanNot(), cmp);
|
| - return Replace(inv);
|
| + // JSUnaryNot(x:boolean,context) => BooleanNot(x)
|
| + node->set_op(simplified()->BooleanNot());
|
| + node->TrimInputCount(1);
|
| + return Changed(node);
|
| }
|
| - return NoChange();
|
| + // JSUnaryNot(x,context) => BooleanNot(AnyToBoolean(x))
|
| + node->set_op(simplified()->BooleanNot());
|
| + node->ReplaceInput(0, graph()->NewNode(simplified()->AnyToBoolean(), input));
|
| + node->TrimInputCount(1);
|
| + return Changed(node);
|
| }
|
|
|
|
|
| Reduction JSTypedLowering::ReduceJSToBoolean(Node* node) {
|
| - // Try to reduce the input first.
|
| - Node* const input = node->InputAt(0);
|
| - Reduction reduction = ReduceJSToBooleanInput(input);
|
| - if (reduction.Changed()) return reduction;
|
| - if (input->opcode() == IrOpcode::kPhi) {
|
| - // JSToBoolean(phi(x1,...,xn,control),context)
|
| - // => phi(JSToBoolean(x1,no-context),...,JSToBoolean(xn,no-context))
|
| - int const input_count = input->InputCount() - 1;
|
| - Node* const control = input->InputAt(input_count);
|
| - DCHECK_LE(0, input_count);
|
| - DCHECK(NodeProperties::IsControl(control));
|
| - DCHECK(NodeProperties::GetBounds(node).upper->Is(Type::Boolean()));
|
| - DCHECK(!NodeProperties::GetBounds(input).upper->Is(Type::Boolean()));
|
| - node->set_op(common()->Phi(kMachAnyTagged, input_count));
|
| - for (int i = 0; i < input_count; ++i) {
|
| - // We must be very careful not to introduce cycles when pushing
|
| - // operations into phis. It is safe for {value}, since it appears
|
| - // as input to the phi that we are replacing, but it's not safe
|
| - // to simply reuse the context of the {node}. However, ToBoolean()
|
| - // does not require a context anyways, so it's safe to discard it
|
| - // here and pass the dummy context.
|
| - Node* const value = ConvertToBoolean(input->InputAt(i));
|
| - if (i < node->InputCount()) {
|
| - node->ReplaceInput(i, value);
|
| - } else {
|
| - node->AppendInput(graph()->zone(), value);
|
| - }
|
| - }
|
| - if (input_count < node->InputCount()) {
|
| - node->ReplaceInput(input_count, control);
|
| - } else {
|
| - node->AppendInput(graph()->zone(), control);
|
| - }
|
| - node->TrimInputCount(input_count + 1);
|
| - return Changed(node);
|
| - }
|
| - if (input->opcode() == IrOpcode::kSelect) {
|
| - // JSToBoolean(select(c,x1,x2),context)
|
| - // => select(c,JSToBoolean(x1,no-context),...,JSToBoolean(x2,no-context))
|
| - int const input_count = input->InputCount();
|
| - BranchHint const input_hint = SelectParametersOf(input->op()).hint();
|
| - DCHECK_EQ(3, input_count);
|
| - DCHECK(NodeProperties::GetBounds(node).upper->Is(Type::Boolean()));
|
| - DCHECK(!NodeProperties::GetBounds(input).upper->Is(Type::Boolean()));
|
| - node->set_op(common()->Select(kMachAnyTagged, input_hint));
|
| - node->InsertInput(graph()->zone(), 0, input->InputAt(0));
|
| - for (int i = 1; i < input_count; ++i) {
|
| - // We must be very careful not to introduce cycles when pushing
|
| - // operations into selects. It is safe for {value}, since it appears
|
| - // as input to the select that we are replacing, but it's not safe
|
| - // to simply reuse the context of the {node}. However, ToBoolean()
|
| - // does not require a context anyways, so it's safe to discard it
|
| - // here and pass the dummy context.
|
| - Node* const value = ConvertToBoolean(input->InputAt(i));
|
| - node->ReplaceInput(i, value);
|
| - }
|
| - DCHECK_EQ(3, node->InputCount());
|
| - return Changed(node);
|
| - }
|
| - InsertConversion(node);
|
| - if (node->InputAt(1) != jsgraph()->NoContextConstant()) {
|
| - // JSToBoolean(x,context) => JSToBoolean(x,no-context)
|
| - node->ReplaceInput(1, jsgraph()->NoContextConstant());
|
| - return Changed(node);
|
| + Node* input = node->InputAt(0);
|
| + Type* input_type = NodeProperties::GetBounds(input).upper;
|
| + if (input_type->Is(Type::Boolean())) {
|
| + // JSToBoolean(x:boolean,context) => x
|
| + return Replace(input);
|
| }
|
| - return NoChange();
|
| + // JSToBoolean(x,context) => AnyToBoolean(x)
|
| + node->set_op(simplified()->AnyToBoolean());
|
| + node->TrimInputCount(1);
|
| + return Changed(node);
|
| }
|
|
|
|
|
| @@ -972,18 +882,8 @@ Reduction JSTypedLowering::Reduce(Node* node) {
|
| return ReduceNumberBinop(node, simplified()->NumberDivide());
|
| case IrOpcode::kJSModulus:
|
| return ReduceNumberBinop(node, simplified()->NumberModulus());
|
| - case IrOpcode::kJSUnaryNot: {
|
| - Reduction result = ReduceJSToBooleanInput(node->InputAt(0));
|
| - if (result.Changed()) {
|
| - // JSUnaryNot(x:boolean) => BooleanNot(x)
|
| - node = result.replacement();
|
| - } else {
|
| - // JSUnaryNot(x) => BooleanNot(JSToBoolean(x))
|
| - node->set_op(javascript()->ToBoolean());
|
| - }
|
| - Node* value = graph()->NewNode(simplified()->BooleanNot(), node);
|
| - return Replace(value);
|
| - }
|
| + case IrOpcode::kJSUnaryNot:
|
| + return ReduceJSUnaryNot(node);
|
| case IrOpcode::kJSToBoolean:
|
| return ReduceJSToBoolean(node);
|
| case IrOpcode::kJSToNumber:
|
| @@ -1005,17 +905,6 @@ Reduction JSTypedLowering::Reduce(Node* node) {
|
| }
|
|
|
|
|
| -Node* JSTypedLowering::ConvertToBoolean(Node* input) {
|
| - // Avoid inserting too many eager ToBoolean() operations.
|
| - Reduction const reduction = ReduceJSToBooleanInput(input);
|
| - if (reduction.Changed()) return reduction.replacement();
|
| - Node* const conversion = graph()->NewNode(javascript()->ToBoolean(), input,
|
| - jsgraph()->NoContextConstant());
|
| - InsertConversion(conversion);
|
| - return conversion;
|
| -}
|
| -
|
| -
|
| Node* JSTypedLowering::ConvertToNumber(Node* input) {
|
| DCHECK(NodeProperties::GetBounds(input).upper->Is(Type::PlainPrimitive()));
|
| // Avoid inserting too many eager ToNumber() operations.
|
| @@ -1043,8 +932,7 @@ Node* JSTypedLowering::FindConversion(Node* input) {
|
|
|
|
|
| void JSTypedLowering::InsertConversion(Node* conversion) {
|
| - DCHECK(conversion->opcode() == IrOpcode::kJSToBoolean ||
|
| - conversion->opcode() == IrOpcode::kJSToNumber);
|
| + DCHECK(conversion->opcode() == IrOpcode::kJSToNumber);
|
| size_t const input_id = conversion->InputAt(0)->id();
|
| if (input_id >= conversions_.size()) {
|
| conversions_.resize(2 * input_id + 1);
|
|
|