| OLD | NEW | 
|---|
| 1 // Copyright 2015 the V8 project authors. All rights reserved. | 1 // Copyright 2015 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/instruction-scheduler.h" | 5 #include "src/compiler/instruction-scheduler.h" | 
| 6 | 6 | 
| 7 #include "src/base/adapters.h" | 7 #include "src/base/adapters.h" | 
| 8 #include "src/base/utils/random-number-generator.h" | 8 #include "src/base/utils/random-number-generator.h" | 
| 9 | 9 | 
| 10 namespace v8 { | 10 namespace v8 { | 
| (...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 75 } | 75 } | 
| 76 | 76 | 
| 77 | 77 | 
| 78 InstructionScheduler::InstructionScheduler(Zone* zone, | 78 InstructionScheduler::InstructionScheduler(Zone* zone, | 
| 79                                            InstructionSequence* sequence) | 79                                            InstructionSequence* sequence) | 
| 80     : zone_(zone), | 80     : zone_(zone), | 
| 81       sequence_(sequence), | 81       sequence_(sequence), | 
| 82       graph_(zone), | 82       graph_(zone), | 
| 83       last_side_effect_instr_(nullptr), | 83       last_side_effect_instr_(nullptr), | 
| 84       pending_loads_(zone), | 84       pending_loads_(zone), | 
| 85       last_live_in_reg_marker_(nullptr) { | 85       last_live_in_reg_marker_(nullptr), | 
|  | 86       last_deopt_(nullptr) { | 
| 86 } | 87 } | 
| 87 | 88 | 
| 88 | 89 | 
| 89 void InstructionScheduler::StartBlock(RpoNumber rpo) { | 90 void InstructionScheduler::StartBlock(RpoNumber rpo) { | 
| 90   DCHECK(graph_.empty()); | 91   DCHECK(graph_.empty()); | 
| 91   DCHECK(last_side_effect_instr_ == nullptr); | 92   DCHECK(last_side_effect_instr_ == nullptr); | 
| 92   DCHECK(pending_loads_.empty()); | 93   DCHECK(pending_loads_.empty()); | 
| 93   DCHECK(last_live_in_reg_marker_ == nullptr); | 94   DCHECK(last_live_in_reg_marker_ == nullptr); | 
|  | 95   DCHECK(last_deopt_ == nullptr); | 
| 94   sequence()->StartBlock(rpo); | 96   sequence()->StartBlock(rpo); | 
| 95 } | 97 } | 
| 96 | 98 | 
| 97 | 99 | 
| 98 void InstructionScheduler::EndBlock(RpoNumber rpo) { | 100 void InstructionScheduler::EndBlock(RpoNumber rpo) { | 
| 99   if (FLAG_turbo_stress_instruction_scheduling) { | 101   if (FLAG_turbo_stress_instruction_scheduling) { | 
| 100     ScheduleBlock<StressSchedulerQueue>(); | 102     ScheduleBlock<StressSchedulerQueue>(); | 
| 101   } else { | 103   } else { | 
| 102     ScheduleBlock<CriticalPathFirstQueue>(); | 104     ScheduleBlock<CriticalPathFirstQueue>(); | 
| 103   } | 105   } | 
| 104   sequence()->EndBlock(rpo); | 106   sequence()->EndBlock(rpo); | 
| 105   graph_.clear(); | 107   graph_.clear(); | 
| 106   last_side_effect_instr_ = nullptr; | 108   last_side_effect_instr_ = nullptr; | 
| 107   pending_loads_.clear(); | 109   pending_loads_.clear(); | 
| 108   last_live_in_reg_marker_ = nullptr; | 110   last_live_in_reg_marker_ = nullptr; | 
|  | 111   last_deopt_ = nullptr; | 
| 109 } | 112 } | 
| 110 | 113 | 
| 111 | 114 | 
| 112 void InstructionScheduler::AddInstruction(Instruction* instr) { | 115 void InstructionScheduler::AddInstruction(Instruction* instr) { | 
| 113   ScheduleGraphNode* new_node = new (zone()) ScheduleGraphNode(zone(), instr); | 116   ScheduleGraphNode* new_node = new (zone()) ScheduleGraphNode(zone(), instr); | 
| 114 | 117 | 
| 115   if (IsBlockTerminator(instr)) { | 118   if (IsBlockTerminator(instr)) { | 
| 116     // Make sure that basic block terminators are not moved by adding them | 119     // Make sure that basic block terminators are not moved by adding them | 
| 117     // as successor of every instruction. | 120     // as successor of every instruction. | 
| 118     for (ScheduleGraphNode* node : graph_) { | 121     for (ScheduleGraphNode* node : graph_) { | 
| 119       node->AddSuccessor(new_node); | 122       node->AddSuccessor(new_node); | 
| 120     } | 123     } | 
| 121   } else if (IsFixedRegisterParameter(instr)) { | 124   } else if (IsFixedRegisterParameter(instr)) { | 
| 122     if (last_live_in_reg_marker_ != nullptr) { | 125     if (last_live_in_reg_marker_ != nullptr) { | 
| 123       last_live_in_reg_marker_->AddSuccessor(new_node); | 126       last_live_in_reg_marker_->AddSuccessor(new_node); | 
| 124     } | 127     } | 
| 125     last_live_in_reg_marker_ = new_node; | 128     last_live_in_reg_marker_ = new_node; | 
| 126   } else { | 129   } else { | 
| 127     if (last_live_in_reg_marker_ != nullptr) { | 130     if (last_live_in_reg_marker_ != nullptr) { | 
| 128       last_live_in_reg_marker_->AddSuccessor(new_node); | 131       last_live_in_reg_marker_->AddSuccessor(new_node); | 
| 129     } | 132     } | 
| 130 | 133 | 
|  | 134     // Make sure that new instructions are not scheduled before the last | 
|  | 135     // deoptimization point. | 
|  | 136     if (last_deopt_ != nullptr) { | 
|  | 137       last_deopt_->AddSuccessor(new_node); | 
|  | 138     } | 
|  | 139 | 
| 131     // Instructions with side effects and memory operations can't be | 140     // Instructions with side effects and memory operations can't be | 
| 132     // reordered with respect to each other. | 141     // reordered with respect to each other. | 
| 133     if (HasSideEffect(instr)) { | 142     if (HasSideEffect(instr)) { | 
| 134       if (last_side_effect_instr_ != nullptr) { | 143       if (last_side_effect_instr_ != nullptr) { | 
| 135         last_side_effect_instr_->AddSuccessor(new_node); | 144         last_side_effect_instr_->AddSuccessor(new_node); | 
| 136       } | 145       } | 
| 137       for (ScheduleGraphNode* load : pending_loads_) { | 146       for (ScheduleGraphNode* load : pending_loads_) { | 
| 138         load->AddSuccessor(new_node); | 147         load->AddSuccessor(new_node); | 
| 139       } | 148       } | 
| 140       pending_loads_.clear(); | 149       pending_loads_.clear(); | 
| 141       last_side_effect_instr_ = new_node; | 150       last_side_effect_instr_ = new_node; | 
| 142     } else if (IsLoadOperation(instr)) { | 151     } else if (IsLoadOperation(instr)) { | 
| 143       // Load operations can't be reordered with side effects instructions but | 152       // Load operations can't be reordered with side effects instructions but | 
| 144       // independent loads can be reordered with respect to each other. | 153       // independent loads can be reordered with respect to each other. | 
| 145       if (last_side_effect_instr_ != nullptr) { | 154       if (last_side_effect_instr_ != nullptr) { | 
| 146         last_side_effect_instr_->AddSuccessor(new_node); | 155         last_side_effect_instr_->AddSuccessor(new_node); | 
| 147       } | 156       } | 
| 148       pending_loads_.push_back(new_node); | 157       pending_loads_.push_back(new_node); | 
|  | 158     } else if (instr->IsDeoptimizeCall()) { | 
|  | 159       // Ensure that deopts are not reordered with respect to side-effect | 
|  | 160       // instructions. | 
|  | 161       if (last_side_effect_instr_ != nullptr) { | 
|  | 162         last_side_effect_instr_->AddSuccessor(new_node); | 
|  | 163       } | 
|  | 164       last_deopt_ = new_node; | 
| 149     } | 165     } | 
| 150 | 166 | 
| 151     // Look for operand dependencies. | 167     // Look for operand dependencies. | 
| 152     for (ScheduleGraphNode* node : graph_) { | 168     for (ScheduleGraphNode* node : graph_) { | 
| 153       if (HasOperandDependency(node->instruction(), instr)) { | 169       if (HasOperandDependency(node->instruction(), instr)) { | 
| 154         node->AddSuccessor(new_node); | 170         node->AddSuccessor(new_node); | 
| 155       } | 171       } | 
| 156     } | 172     } | 
| 157   } | 173   } | 
| 158 | 174 | 
| (...skipping 157 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 316       } | 332       } | 
| 317     } | 333     } | 
| 318 | 334 | 
| 319     node->set_total_latency(max_latency + node->latency()); | 335     node->set_total_latency(max_latency + node->latency()); | 
| 320   } | 336   } | 
| 321 } | 337 } | 
| 322 | 338 | 
| 323 }  // namespace compiler | 339 }  // namespace compiler | 
| 324 }  // namespace internal | 340 }  // namespace internal | 
| 325 }  // namespace v8 | 341 }  // namespace v8 | 
| OLD | NEW | 
|---|