Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(432)

Side by Side Diff: src/compiler/ast-graph-builder.cc

Issue 894073002: [turbofan] Put StructuredGraphBuilder out of its misery and merge its remnants back into the AstGra… (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Created 5 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/compiler/ast-graph-builder.h ('k') | src/compiler/control-builders.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2014 the V8 project authors. All rights reserved. 1 // Copyright 2014 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/compiler/ast-graph-builder.h" 5 #include "src/compiler/ast-graph-builder.h"
6 6
7 #include "src/compiler.h" 7 #include "src/compiler.h"
8 #include "src/compiler/ast-loop-assignment-analyzer.h" 8 #include "src/compiler/ast-loop-assignment-analyzer.h"
9 #include "src/compiler/control-builders.h" 9 #include "src/compiler/control-builders.h"
10 #include "src/compiler/linkage.h" 10 #include "src/compiler/linkage.h"
11 #include "src/compiler/machine-operator.h" 11 #include "src/compiler/machine-operator.h"
12 #include "src/compiler/node-matchers.h" 12 #include "src/compiler/node-matchers.h"
13 #include "src/compiler/node-properties.h" 13 #include "src/compiler/node-properties.h"
14 #include "src/compiler/operator-properties.h" 14 #include "src/compiler/operator-properties.h"
15 #include "src/full-codegen.h" 15 #include "src/full-codegen.h"
16 #include "src/parser.h" 16 #include "src/parser.h"
17 #include "src/scopes.h" 17 #include "src/scopes.h"
18 18
19 namespace v8 { 19 namespace v8 {
20 namespace internal { 20 namespace internal {
21 namespace compiler { 21 namespace compiler {
22 22
23
23 AstGraphBuilder::AstGraphBuilder(Zone* local_zone, CompilationInfo* info, 24 AstGraphBuilder::AstGraphBuilder(Zone* local_zone, CompilationInfo* info,
24 JSGraph* jsgraph, LoopAssignmentAnalysis* loop) 25 JSGraph* jsgraph, LoopAssignmentAnalysis* loop)
25 : StructuredGraphBuilder(jsgraph->isolate(), local_zone, jsgraph->graph(), 26 : local_zone_(local_zone),
26 jsgraph->common()),
27 info_(info), 27 info_(info),
28 jsgraph_(jsgraph), 28 jsgraph_(jsgraph),
29 environment_(nullptr),
30 ast_context_(nullptr),
29 globals_(0, local_zone), 31 globals_(0, local_zone),
30 breakable_(NULL), 32 breakable_(nullptr),
31 execution_context_(NULL), 33 execution_context_(nullptr),
34 input_buffer_size_(0),
35 input_buffer_(nullptr),
36 current_context_(nullptr),
37 exit_control_(nullptr),
32 loop_assignment_analysis_(loop) { 38 loop_assignment_analysis_(loop) {
33 InitializeAstVisitor(info->isolate(), local_zone); 39 InitializeAstVisitor(info->isolate(), local_zone);
34 } 40 }
35 41
36 42
37 Node* AstGraphBuilder::GetFunctionClosure() { 43 Node* AstGraphBuilder::GetFunctionClosure() {
38 if (!function_closure_.is_set()) { 44 if (!function_closure_.is_set()) {
39 const Operator* op = 45 const Operator* op =
40 common()->Parameter(Linkage::kJSFunctionCallClosureParamIndex); 46 common()->Parameter(Linkage::kJSFunctionCallClosureParamIndex);
41 Node* node = NewNode(op, graph()->start()); 47 Node* node = NewNode(op, graph()->start());
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after
144 Property* property = expr->AsProperty(); 150 Property* property = expr->AsProperty();
145 DCHECK(expr->IsValidReferenceExpression()); 151 DCHECK(expr->IsValidReferenceExpression());
146 LhsKind lhs_kind = 152 LhsKind lhs_kind =
147 (property == NULL) ? VARIABLE : (property->key()->IsPropertyName()) 153 (property == NULL) ? VARIABLE : (property->key()->IsPropertyName())
148 ? NAMED_PROPERTY 154 ? NAMED_PROPERTY
149 : KEYED_PROPERTY; 155 : KEYED_PROPERTY;
150 return lhs_kind; 156 return lhs_kind;
151 } 157 }
152 158
153 159
154 StructuredGraphBuilder::Environment* AstGraphBuilder::CopyEnvironment(
155 StructuredGraphBuilder::Environment* env) {
156 return new (zone()) Environment(*reinterpret_cast<Environment*>(env));
157 }
158
159
160 AstGraphBuilder::Environment::Environment(AstGraphBuilder* builder, 160 AstGraphBuilder::Environment::Environment(AstGraphBuilder* builder,
161 Scope* scope, 161 Scope* scope,
162 Node* control_dependency) 162 Node* control_dependency)
163 : StructuredGraphBuilder::Environment(builder, control_dependency), 163 : builder_(builder),
164 parameters_count_(scope->num_parameters() + 1), 164 parameters_count_(scope->num_parameters() + 1),
165 locals_count_(scope->num_stack_slots()), 165 locals_count_(scope->num_stack_slots()),
166 parameters_node_(NULL), 166 values_(builder_->local_zone()),
167 locals_node_(NULL), 167 control_dependency_(control_dependency),
168 stack_node_(NULL) { 168 effect_dependency_(control_dependency),
169 parameters_node_(nullptr),
170 locals_node_(nullptr),
171 stack_node_(nullptr) {
169 DCHECK_EQ(scope->num_parameters() + 1, parameters_count()); 172 DCHECK_EQ(scope->num_parameters() + 1, parameters_count());
170 173
171 // Bind the receiver variable. 174 // Bind the receiver variable.
172 Node* receiver = builder->graph()->NewNode(common()->Parameter(0), 175 Node* receiver = builder->graph()->NewNode(common()->Parameter(0),
173 builder->graph()->start()); 176 builder->graph()->start());
174 values()->push_back(receiver); 177 values()->push_back(receiver);
175 178
176 // Bind all parameter variables. The parameter indices are shifted by 1 179 // Bind all parameter variables. The parameter indices are shifted by 1
177 // (receiver is parameter index -1 but environment index 0). 180 // (receiver is parameter index -1 but environment index 0).
178 for (int i = 0; i < scope->num_parameters(); ++i) { 181 for (int i = 0; i < scope->num_parameters(); ++i) {
179 Node* parameter = builder->graph()->NewNode(common()->Parameter(i + 1), 182 Node* parameter = builder->graph()->NewNode(common()->Parameter(i + 1),
180 builder->graph()->start()); 183 builder->graph()->start());
181 values()->push_back(parameter); 184 values()->push_back(parameter);
182 } 185 }
183 186
184 // Bind all local variables to undefined. 187 // Bind all local variables to undefined.
185 Node* undefined_constant = builder->jsgraph()->UndefinedConstant(); 188 Node* undefined_constant = builder->jsgraph()->UndefinedConstant();
186 values()->insert(values()->end(), locals_count(), undefined_constant); 189 values()->insert(values()->end(), locals_count(), undefined_constant);
187 } 190 }
188 191
189 192
190 AstGraphBuilder::Environment::Environment(const Environment& copy) 193 AstGraphBuilder::Environment::Environment(
191 : StructuredGraphBuilder::Environment( 194 const AstGraphBuilder::Environment* copy)
192 static_cast<StructuredGraphBuilder::Environment>(copy)), 195 : builder_(copy->builder_),
193 parameters_count_(copy.parameters_count_), 196 parameters_count_(copy->parameters_count_),
194 locals_count_(copy.locals_count_), 197 locals_count_(copy->locals_count_),
195 parameters_node_(copy.parameters_node_), 198 values_(copy->zone()),
196 locals_node_(copy.locals_node_), 199 control_dependency_(copy->control_dependency_),
197 stack_node_(copy.stack_node_) {} 200 effect_dependency_(copy->effect_dependency_),
201 parameters_node_(copy->parameters_node_),
202 locals_node_(copy->locals_node_),
203 stack_node_(copy->stack_node_) {
204 const size_t kStackEstimate = 7; // optimum from experimentation!
205 values_.reserve(copy->values_.size() + kStackEstimate);
206 values_.insert(values_.begin(), copy->values_.begin(), copy->values_.end());
207 }
198 208
199 209
200 void AstGraphBuilder::Environment::UpdateStateValues(Node** state_values, 210 void AstGraphBuilder::Environment::UpdateStateValues(Node** state_values,
201 int offset, int count) { 211 int offset, int count) {
202 bool should_update = false; 212 bool should_update = false;
203 Node** env_values = (count == 0) ? NULL : &values()->at(offset); 213 Node** env_values = (count == 0) ? NULL : &values()->at(offset);
204 if (*state_values == NULL || (*state_values)->InputCount() != count) { 214 if (*state_values == NULL || (*state_values)->InputCount() != count) {
205 should_update = true; 215 should_update = true;
206 } else { 216 } else {
207 DCHECK(static_cast<size_t>(offset + count) <= values()->size()); 217 DCHECK(static_cast<size_t>(offset + count) <= values()->size());
(...skipping 14 matching lines...) Expand all
222 Node* AstGraphBuilder::Environment::Checkpoint( 232 Node* AstGraphBuilder::Environment::Checkpoint(
223 BailoutId ast_id, OutputFrameStateCombine combine) { 233 BailoutId ast_id, OutputFrameStateCombine combine) {
224 UpdateStateValues(&parameters_node_, 0, parameters_count()); 234 UpdateStateValues(&parameters_node_, 0, parameters_count());
225 UpdateStateValues(&locals_node_, parameters_count(), locals_count()); 235 UpdateStateValues(&locals_node_, parameters_count(), locals_count());
226 UpdateStateValues(&stack_node_, parameters_count() + locals_count(), 236 UpdateStateValues(&stack_node_, parameters_count() + locals_count(),
227 stack_height()); 237 stack_height());
228 238
229 const Operator* op = common()->FrameState(JS_FRAME, ast_id, combine); 239 const Operator* op = common()->FrameState(JS_FRAME, ast_id, combine);
230 240
231 return graph()->NewNode(op, parameters_node_, locals_node_, stack_node_, 241 return graph()->NewNode(op, parameters_node_, locals_node_, stack_node_,
232 GetContext(), 242 builder()->current_context(),
233 builder()->jsgraph()->UndefinedConstant()); 243 builder()->jsgraph()->UndefinedConstant());
234 } 244 }
235 245
236 246
237 AstGraphBuilder::AstContext::AstContext(AstGraphBuilder* own, 247 AstGraphBuilder::AstContext::AstContext(AstGraphBuilder* own,
238 Expression::Context kind) 248 Expression::Context kind)
239 : kind_(kind), owner_(own), outer_(own->ast_context()) { 249 : kind_(kind), owner_(own), outer_(own->ast_context()) {
240 owner()->set_ast_context(this); // Push. 250 owner()->set_ast_context(this); // Push.
241 #ifdef DEBUG 251 #ifdef DEBUG
242 original_height_ = environment()->stack_height(); 252 original_height_ = environment()->stack_height();
(...skipping 268 matching lines...) Expand 10 before | Expand all | Expand 10 after
511 compare_if.If(condition); 521 compare_if.If(condition);
512 compare_if.Then(); 522 compare_if.Then();
513 Visit(stmt->then_statement()); 523 Visit(stmt->then_statement());
514 compare_if.Else(); 524 compare_if.Else();
515 Visit(stmt->else_statement()); 525 Visit(stmt->else_statement());
516 compare_if.End(); 526 compare_if.End();
517 } 527 }
518 528
519 529
520 void AstGraphBuilder::VisitContinueStatement(ContinueStatement* stmt) { 530 void AstGraphBuilder::VisitContinueStatement(ContinueStatement* stmt) {
521 StructuredGraphBuilder::Environment* env = environment()->CopyAsUnreachable(); 531 Environment* env = environment()->CopyAsUnreachable();
522 breakable()->ContinueTarget(stmt->target()); 532 breakable()->ContinueTarget(stmt->target());
523 set_environment(env); 533 set_environment(env);
524 } 534 }
525 535
526 536
527 void AstGraphBuilder::VisitBreakStatement(BreakStatement* stmt) { 537 void AstGraphBuilder::VisitBreakStatement(BreakStatement* stmt) {
528 StructuredGraphBuilder::Environment* env = environment()->CopyAsUnreachable(); 538 Environment* env = environment()->CopyAsUnreachable();
529 breakable()->BreakTarget(stmt->target()); 539 breakable()->BreakTarget(stmt->target());
530 set_environment(env); 540 set_environment(env);
531 } 541 }
532 542
533 543
534 void AstGraphBuilder::VisitReturnStatement(ReturnStatement* stmt) { 544 void AstGraphBuilder::VisitReturnStatement(ReturnStatement* stmt) {
535 VisitForValue(stmt->expression()); 545 VisitForValue(stmt->expression());
536 Node* result = environment()->Pop(); 546 Node* result = environment()->Pop();
537 Node* control = NewNode(common()->Return(), result); 547 Node* control = NewNode(common()->Return(), result);
538 UpdateControlDependencyToLeaveFunction(control); 548 UpdateControlDependencyToLeaveFunction(control);
(...skipping 1399 matching lines...) Expand 10 before | Expand all | Expand 10 after
1938 } 1948 }
1939 Node* value = NewNode(op, arity, all); 1949 Node* value = NewNode(op, arity, all);
1940 return value; 1950 return value;
1941 } 1951 }
1942 1952
1943 1953
1944 Node* AstGraphBuilder::BuildPatchReceiverToGlobalProxy(Node* receiver) { 1954 Node* AstGraphBuilder::BuildPatchReceiverToGlobalProxy(Node* receiver) {
1945 // Sloppy mode functions and builtins need to replace the receiver with the 1955 // Sloppy mode functions and builtins need to replace the receiver with the
1946 // global proxy when called as functions (without an explicit receiver 1956 // global proxy when called as functions (without an explicit receiver
1947 // object). Otherwise there is nothing left to do here. 1957 // object). Otherwise there is nothing left to do here.
1948 if (info()->strict_mode() != SLOPPY || info()->is_native()) return receiver; 1958 if (strict_mode() != SLOPPY || info()->is_native()) return receiver;
1949 1959
1950 // There is no need to perform patching if the receiver is never used. Note 1960 // There is no need to perform patching if the receiver is never used. Note
1951 // that scope predicates are purely syntactical, a call to eval might still 1961 // that scope predicates are purely syntactical, a call to eval might still
1952 // inspect the receiver value. 1962 // inspect the receiver value.
1953 if (!info()->scope()->uses_this() && !info()->scope()->inner_uses_this() && 1963 if (!info()->scope()->uses_this() && !info()->scope()->inner_uses_this() &&
1954 !info()->scope()->calls_sloppy_eval()) { 1964 !info()->scope()->calls_sloppy_eval()) {
1955 return receiver; 1965 return receiver;
1956 } 1966 }
1957 1967
1958 IfBuilder receiver_check(this); 1968 IfBuilder receiver_check(this);
(...skipping 473 matching lines...) Expand 10 before | Expand all | Expand 10 after
2432 } 2442 }
2433 } 2443 }
2434 2444
2435 2445
2436 BitVector* AstGraphBuilder::GetVariablesAssignedInLoop( 2446 BitVector* AstGraphBuilder::GetVariablesAssignedInLoop(
2437 IterationStatement* stmt) { 2447 IterationStatement* stmt) {
2438 if (loop_assignment_analysis_ == NULL) return NULL; 2448 if (loop_assignment_analysis_ == NULL) return NULL;
2439 return loop_assignment_analysis_->GetVariablesAssignedInLoop(stmt); 2449 return loop_assignment_analysis_->GetVariablesAssignedInLoop(stmt);
2440 } 2450 }
2441 2451
2452
2453 Node** AstGraphBuilder::EnsureInputBufferSize(int size) {
2454 if (size > input_buffer_size_) {
2455 size = size + kInputBufferSizeIncrement + input_buffer_size_;
2456 input_buffer_ = local_zone()->NewArray<Node*>(size);
2457 input_buffer_size_ = size;
2458 }
2459 return input_buffer_;
2460 }
2461
2462
2463 Node* AstGraphBuilder::MakeNode(const Operator* op, int value_input_count,
2464 Node** value_inputs, bool incomplete) {
2465 DCHECK(op->ValueInputCount() == value_input_count);
2466
2467 bool has_context = OperatorProperties::HasContextInput(op);
2468 bool has_framestate = OperatorProperties::HasFrameStateInput(op);
2469 bool has_control = op->ControlInputCount() == 1;
2470 bool has_effect = op->EffectInputCount() == 1;
2471
2472 DCHECK(op->ControlInputCount() < 2);
2473 DCHECK(op->EffectInputCount() < 2);
2474
2475 Node* result = NULL;
2476 if (!has_context && !has_framestate && !has_control && !has_effect) {
2477 result = graph()->NewNode(op, value_input_count, value_inputs, incomplete);
2478 } else {
2479 int input_count_with_deps = value_input_count;
2480 if (has_context) ++input_count_with_deps;
2481 if (has_framestate) ++input_count_with_deps;
2482 if (has_control) ++input_count_with_deps;
2483 if (has_effect) ++input_count_with_deps;
2484 Node** buffer = EnsureInputBufferSize(input_count_with_deps);
2485 memcpy(buffer, value_inputs, kPointerSize * value_input_count);
2486 Node** current_input = buffer + value_input_count;
2487 if (has_context) {
2488 *current_input++ = current_context();
2489 }
2490 if (has_framestate) {
2491 // The frame state will be inserted later. Here we misuse
2492 // the dead_control node as a sentinel to be later overwritten
2493 // with the real frame state.
2494 *current_input++ = dead_control();
2495 }
2496 if (has_effect) {
2497 *current_input++ = environment_->GetEffectDependency();
2498 }
2499 if (has_control) {
2500 *current_input++ = environment_->GetControlDependency();
2501 }
2502 result = graph()->NewNode(op, input_count_with_deps, buffer, incomplete);
2503 if (has_effect) {
2504 environment_->UpdateEffectDependency(result);
2505 }
2506 if (result->op()->ControlOutputCount() > 0 &&
2507 !environment()->IsMarkedAsUnreachable()) {
2508 environment_->UpdateControlDependency(result);
2509 }
2510 }
2511
2512 return result;
2513 }
2514
2515
2516 void AstGraphBuilder::UpdateControlDependencyToLeaveFunction(Node* exit) {
2517 if (environment()->IsMarkedAsUnreachable()) return;
2518 if (exit_control() != NULL) {
2519 exit = MergeControl(exit_control(), exit);
2520 }
2521 environment()->MarkAsUnreachable();
2522 set_exit_control(exit);
2523 }
2524
2525
2526 void AstGraphBuilder::Environment::Merge(Environment* other) {
2527 DCHECK(values_.size() == other->values_.size());
2528
2529 // Nothing to do if the other environment is dead.
2530 if (other->IsMarkedAsUnreachable()) return;
2531
2532 // Resurrect a dead environment by copying the contents of the other one and
2533 // placing a singleton merge as the new control dependency.
2534 if (this->IsMarkedAsUnreachable()) {
2535 Node* other_control = other->control_dependency_;
2536 Node* inputs[] = {other_control};
2537 control_dependency_ =
2538 graph()->NewNode(common()->Merge(1), arraysize(inputs), inputs, true);
2539 effect_dependency_ = other->effect_dependency_;
2540 values_ = other->values_;
2541 return;
2542 }
2543
2544 // Create a merge of the control dependencies of both environments and update
2545 // the current environment's control dependency accordingly.
2546 Node* control = builder_->MergeControl(this->GetControlDependency(),
2547 other->GetControlDependency());
2548 UpdateControlDependency(control);
2549
2550 // Create a merge of the effect dependencies of both environments and update
2551 // the current environment's effect dependency accordingly.
2552 Node* effect = builder_->MergeEffect(this->GetEffectDependency(),
2553 other->GetEffectDependency(), control);
2554 UpdateEffectDependency(effect);
2555
2556 // Introduce Phi nodes for values that have differing input at merge points,
2557 // potentially extending an existing Phi node if possible.
2558 for (int i = 0; i < static_cast<int>(values_.size()); ++i) {
2559 values_[i] = builder_->MergeValue(values_[i], other->values_[i], control);
2560 }
2561 }
2562
2563
2564 void AstGraphBuilder::Environment::PrepareForLoop(BitVector* assigned,
2565 bool is_osr) {
2566 int size = static_cast<int>(values()->size());
2567
2568 Node* control = builder_->NewLoop();
2569 if (assigned == nullptr) {
2570 // Assume that everything is updated in the loop.
2571 for (int i = 0; i < size; ++i) {
2572 Node* phi = builder_->NewPhi(1, values()->at(i), control);
2573 values()->at(i) = phi;
2574 }
2575 } else {
2576 // Only build phis for those locals assigned in this loop.
2577 for (int i = 0; i < size; ++i) {
2578 if (i < assigned->length() && !assigned->Contains(i)) continue;
2579 Node* phi = builder_->NewPhi(1, values()->at(i), control);
2580 values()->at(i) = phi;
2581 }
2582 }
2583 Node* effect = builder_->NewEffectPhi(1, GetEffectDependency(), control);
2584 UpdateEffectDependency(effect);
2585
2586 if (is_osr) {
2587 // Merge OSR values as inputs to the phis of the loop.
2588 Graph* graph = builder_->graph();
2589 Node* osr_loop_entry = builder_->graph()->NewNode(
2590 builder_->common()->OsrLoopEntry(), graph->start(), graph->start());
2591
2592 builder_->MergeControl(control, osr_loop_entry);
2593 builder_->MergeEffect(effect, osr_loop_entry, control);
2594
2595 for (int i = 0; i < size; ++i) {
2596 Node* val = values()->at(i);
2597 if (!IrOpcode::IsConstantOpcode(val->opcode())) {
2598 Node* osr_value =
2599 graph->NewNode(builder_->common()->OsrValue(i), osr_loop_entry);
2600 values()->at(i) = builder_->MergeValue(val, osr_value, control);
2601 }
2602 }
2603 }
2604 }
2605
2606
2607 Node* AstGraphBuilder::NewPhi(int count, Node* input, Node* control) {
2608 const Operator* phi_op = common()->Phi(kMachAnyTagged, count);
2609 Node** buffer = EnsureInputBufferSize(count + 1);
2610 MemsetPointer(buffer, input, count);
2611 buffer[count] = control;
2612 return graph()->NewNode(phi_op, count + 1, buffer, true);
2613 }
2614
2615
2616 // TODO(mstarzinger): Revisit this once we have proper effect states.
2617 Node* AstGraphBuilder::NewEffectPhi(int count, Node* input, Node* control) {
2618 const Operator* phi_op = common()->EffectPhi(count);
2619 Node** buffer = EnsureInputBufferSize(count + 1);
2620 MemsetPointer(buffer, input, count);
2621 buffer[count] = control;
2622 return graph()->NewNode(phi_op, count + 1, buffer, true);
2623 }
2624
2625
2626 Node* AstGraphBuilder::MergeControl(Node* control, Node* other) {
2627 int inputs = control->op()->ControlInputCount() + 1;
2628 if (control->opcode() == IrOpcode::kLoop) {
2629 // Control node for loop exists, add input.
2630 const Operator* op = common()->Loop(inputs);
2631 control->AppendInput(graph_zone(), other);
2632 control->set_op(op);
2633 } else if (control->opcode() == IrOpcode::kMerge) {
2634 // Control node for merge exists, add input.
2635 const Operator* op = common()->Merge(inputs);
2636 control->AppendInput(graph_zone(), other);
2637 control->set_op(op);
2638 } else {
2639 // Control node is a singleton, introduce a merge.
2640 const Operator* op = common()->Merge(inputs);
2641 Node* inputs[] = {control, other};
2642 control = graph()->NewNode(op, arraysize(inputs), inputs, true);
2643 }
2644 return control;
2645 }
2646
2647
2648 Node* AstGraphBuilder::MergeEffect(Node* value, Node* other, Node* control) {
2649 int inputs = control->op()->ControlInputCount();
2650 if (value->opcode() == IrOpcode::kEffectPhi &&
2651 NodeProperties::GetControlInput(value) == control) {
2652 // Phi already exists, add input.
2653 value->set_op(common()->EffectPhi(inputs));
2654 value->InsertInput(graph_zone(), inputs - 1, other);
2655 } else if (value != other) {
2656 // Phi does not exist yet, introduce one.
2657 value = NewEffectPhi(inputs, value, control);
2658 value->ReplaceInput(inputs - 1, other);
2659 }
2660 return value;
2661 }
2662
2663
2664 Node* AstGraphBuilder::MergeValue(Node* value, Node* other, Node* control) {
2665 int inputs = control->op()->ControlInputCount();
2666 if (value->opcode() == IrOpcode::kPhi &&
2667 NodeProperties::GetControlInput(value) == control) {
2668 // Phi already exists, add input.
2669 value->set_op(common()->Phi(kMachAnyTagged, inputs));
2670 value->InsertInput(graph_zone(), inputs - 1, other);
2671 } else if (value != other) {
2672 // Phi does not exist yet, introduce one.
2673 value = NewPhi(inputs, value, control);
2674 value->ReplaceInput(inputs - 1, other);
2675 }
2676 return value;
2677 }
2678
2679
2680 Node* AstGraphBuilder::dead_control() {
2681 if (!dead_control_.is_set()) {
2682 Node* dead_node = graph()->NewNode(common()->Dead());
2683 dead_control_.set(dead_node);
2684 return dead_node;
2685 }
2686 return dead_control_.get();
2687 }
2688
2442 } // namespace compiler 2689 } // namespace compiler
2443 } // namespace internal 2690 } // namespace internal
2444 } // namespace v8 2691 } // namespace v8
OLDNEW
« no previous file with comments | « src/compiler/ast-graph-builder.h ('k') | src/compiler/control-builders.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698