summaryrefslogtreecommitdiff
path: root/deps/v8/src/compiler/common-operator-reducer.cc
diff options
context:
space:
mode:
Diffstat (limited to 'deps/v8/src/compiler/common-operator-reducer.cc')
-rw-r--r--deps/v8/src/compiler/common-operator-reducer.cc56
1 files changed, 48 insertions, 8 deletions
diff --git a/deps/v8/src/compiler/common-operator-reducer.cc b/deps/v8/src/compiler/common-operator-reducer.cc
index d9bc5c8173..2f4888617c 100644
--- a/deps/v8/src/compiler/common-operator-reducer.cc
+++ b/deps/v8/src/compiler/common-operator-reducer.cc
@@ -38,12 +38,14 @@ Decision DecideCondition(Node* const cond) {
CommonOperatorReducer::CommonOperatorReducer(Editor* editor, Graph* graph,
CommonOperatorBuilder* common,
- MachineOperatorBuilder* machine)
+ MachineOperatorBuilder* machine,
+ Zone* temp_zone)
: AdvancedReducer(editor),
graph_(graph),
common_(common),
machine_(machine),
- dead_(graph->NewNode(common->Dead())) {
+ dead_(graph->NewNode(common->Dead())),
+ zone_(temp_zone) {
NodeProperties::SetType(dead_, Type::None());
}
@@ -64,6 +66,8 @@ Reduction CommonOperatorReducer::Reduce(Node* node) {
return ReduceReturn(node);
case IrOpcode::kSelect:
return ReduceSelect(node);
+ case IrOpcode::kSwitch:
+ return ReduceSwitch(node);
default:
break;
}
@@ -138,10 +142,10 @@ Reduction CommonOperatorReducer::ReduceDeoptimizeConditional(Node* node) {
if (condition->opcode() == IrOpcode::kBooleanNot) {
NodeProperties::ReplaceValueInput(node, condition->InputAt(0), 0);
NodeProperties::ChangeOp(
- node, condition_is_true ? common()->DeoptimizeIf(p.kind(), p.reason(),
- VectorSlotPair())
- : common()->DeoptimizeUnless(
- p.kind(), p.reason(), VectorSlotPair()));
+ node,
+ condition_is_true
+ ? common()->DeoptimizeIf(p.kind(), p.reason(), p.feedback())
+ : common()->DeoptimizeUnless(p.kind(), p.reason(), p.feedback()));
return Changed(node);
}
Decision const decision = DecideCondition(condition);
@@ -150,8 +154,8 @@ Reduction CommonOperatorReducer::ReduceDeoptimizeConditional(Node* node) {
ReplaceWithValue(node, dead(), effect, control);
} else {
control = graph()->NewNode(
- common()->Deoptimize(p.kind(), p.reason(), VectorSlotPair()),
- frame_state, effect, control);
+ common()->Deoptimize(p.kind(), p.reason(), p.feedback()), frame_state,
+ effect, control);
// TODO(bmeurer): This should be on the AdvancedReducer somehow.
NodeProperties::MergeControlToEnd(graph(), common(), control);
Revisit(graph()->end());
@@ -414,6 +418,42 @@ Reduction CommonOperatorReducer::ReduceSelect(Node* node) {
return NoChange();
}
+Reduction CommonOperatorReducer::ReduceSwitch(Node* node) {
+ DCHECK_EQ(IrOpcode::kSwitch, node->opcode());
+ Node* const switched_value = node->InputAt(0);
+ Node* const control = node->InputAt(1);
+
+ // Attempt to constant match the switched value against the IfValue cases. If
+ // no case matches, then use the IfDefault. We don't bother marking
+ // non-matching cases as dead code (same for an unused IfDefault), because the
+ // Switch itself will be marked as dead code.
+ Int32Matcher mswitched(switched_value);
+ if (mswitched.HasValue()) {
+ bool matched = false;
+
+ size_t const projection_count = node->op()->ControlOutputCount();
+ Node** projections = zone_->NewArray<Node*>(projection_count);
+ NodeProperties::CollectControlProjections(node, projections,
+ projection_count);
+ for (size_t i = 0; i < projection_count - 1; i++) {
+ Node* if_value = projections[i];
+ DCHECK_EQ(IrOpcode::kIfValue, if_value->opcode());
+ int32_t value_index = OpParameter<int32_t>(if_value->op());
+ if (value_index == mswitched.Value()) {
+ matched = true;
+ Replace(if_value, control);
+ break;
+ }
+ }
+ if (!matched) {
+ Node* if_default = projections[projection_count - 1];
+ DCHECK_EQ(IrOpcode::kIfDefault, if_default->opcode());
+ Replace(if_default, control);
+ }
+ return Replace(dead());
+ }
+ return NoChange();
+}
Reduction CommonOperatorReducer::Change(Node* node, Operator const* op,
Node* a) {