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

Unified Diff: src/compiler/instruction-selector.cc

Issue 2390303002: [turbofan] Check instruction input/output count limits in instruction selector. (Closed)
Patch Set: Fix silly mistakes in the test. Created 4 years, 2 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/compiler/instruction-selector.h ('k') | src/compiler/pipeline.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/compiler/instruction-selector.cc
diff --git a/src/compiler/instruction-selector.cc b/src/compiler/instruction-selector.cc
index d8409a3f89c8250155d645b73b189ece198083d4..e8a3153f7ff90350d83b7ae446af39d7c958bb79 100644
--- a/src/compiler/instruction-selector.cc
+++ b/src/compiler/instruction-selector.cc
@@ -41,11 +41,12 @@ InstructionSelector::InstructionSelector(
virtual_register_rename_(zone),
scheduler_(nullptr),
enable_scheduling_(enable_scheduling),
- frame_(frame) {
+ frame_(frame),
+ instruction_selection_failed_(false) {
instructions_.reserve(node_count);
}
-void InstructionSelector::SelectInstructions() {
+bool InstructionSelector::SelectInstructions() {
// Mark the inputs of all phis in loop headers as used.
BasicBlockVector* blocks = schedule()->rpo_order();
for (auto const block : *blocks) {
@@ -64,6 +65,7 @@ void InstructionSelector::SelectInstructions() {
// Visit each basic block in post order.
for (auto i = blocks->rbegin(); i != blocks->rend(); ++i) {
VisitBlock(*i);
+ if (instruction_selection_failed()) return false;
}
// Schedule the selected instructions.
@@ -90,6 +92,7 @@ void InstructionSelector::SelectInstructions() {
#if DEBUG
sequence()->ValidateSSA();
#endif
+ return true;
}
void InstructionSelector::StartBlock(RpoNumber rpo) {
@@ -208,6 +211,13 @@ Instruction* InstructionSelector::Emit(
InstructionCode opcode, size_t output_count, InstructionOperand* outputs,
size_t input_count, InstructionOperand* inputs, size_t temp_count,
InstructionOperand* temps) {
+ if (output_count >= Instruction::kMaxOutputCount ||
+ input_count >= Instruction::kMaxInputCount ||
+ temp_count >= Instruction::kMaxTempCount) {
+ set_instruction_selection_failed();
+ return nullptr;
+ }
+
Instruction* instr =
Instruction::New(instruction_zone(), opcode, output_count, outputs,
input_count, inputs, temp_count, temps);
@@ -767,7 +777,6 @@ void InstructionSelector::InitializeCallBuffer(Node* call, CallBuffer* buffer,
}
}
-
void InstructionSelector::VisitBlock(BasicBlock* block) {
DCHECK(!current_block_);
current_block_ = block;
@@ -804,6 +813,7 @@ void InstructionSelector::VisitBlock(BasicBlock* block) {
// up".
size_t current_node_end = instructions_.size();
VisitNode(node);
+ if (instruction_selection_failed()) return;
std::reverse(instructions_.begin() + current_node_end, instructions_.end());
if (instructions_.size() == current_node_end) continue;
// Mark source position on first instruction emitted.
@@ -1843,9 +1853,11 @@ void InstructionSelector::VisitCall(Node* node, BasicBlock* handler) {
// Emit the call instruction.
size_t const output_count = buffer.outputs.size();
auto* outputs = output_count ? &buffer.outputs.front() : nullptr;
- Emit(opcode, output_count, outputs, buffer.instruction_args.size(),
- &buffer.instruction_args.front())
- ->MarkAsCall();
+ Instruction* call_instr =
+ Emit(opcode, output_count, outputs, buffer.instruction_args.size(),
+ &buffer.instruction_args.front());
+ if (instruction_selection_failed()) return;
+ call_instr->MarkAsCall();
}
@@ -1951,9 +1963,11 @@ void InstructionSelector::VisitTailCall(Node* node) {
// Emit the call instruction.
size_t output_count = buffer.outputs.size();
auto* outputs = &buffer.outputs.front();
- Emit(opcode, output_count, outputs, buffer.instruction_args.size(),
- &buffer.instruction_args.front())
- ->MarkAsCall();
+ Instruction* call_instr =
+ Emit(opcode, output_count, outputs, buffer.instruction_args.size(),
+ &buffer.instruction_args.front());
+ if (instruction_selection_failed()) return;
+ call_instr->MarkAsCall();
Emit(kArchRet, 0, nullptr, output_count, outputs);
}
}
« no previous file with comments | « src/compiler/instruction-selector.h ('k') | src/compiler/pipeline.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698