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

Unified Diff: src/compiler/osr.cc

Issue 877553007: [turbofan] Gracefully bail out if OSR encounters a loop too deeply nested. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Created 5 years, 11 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/osr.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/osr.cc
diff --git a/src/compiler/osr.cc b/src/compiler/osr.cc
index 3360a1a321f81f86259e56523dffea76e161b58f..6f30963067ab21b9f49873a44952646062fa8c1f 100644
--- a/src/compiler/osr.cc
+++ b/src/compiler/osr.cc
@@ -8,6 +8,7 @@
#include "src/compiler/frame.h"
#include "src/compiler/graph.h"
#include "src/compiler/js-graph.h"
+#include "src/compiler/loop-analysis.h"
#include "src/compiler/node.h"
#include "src/compiler/node-marker.h"
#include "src/compiler/osr.h"
@@ -22,38 +23,51 @@ OsrHelper::OsrHelper(CompilationInfo* info)
stack_slot_count_(info->scope()->num_stack_slots()) {}
-void OsrHelper::Deconstruct(JSGraph* jsgraph, CommonOperatorBuilder* common,
+bool OsrHelper::Deconstruct(JSGraph* jsgraph, CommonOperatorBuilder* common,
Zone* tmp_zone) {
- NodeDeque queue(tmp_zone);
Graph* graph = jsgraph->graph();
- NodeMarker<bool> marker(graph, 2);
- queue.push_back(graph->end());
- marker.Set(graph->end(), true);
-
- while (!queue.empty()) {
- Node* node = queue.front();
- queue.pop_front();
-
- // Rewrite OSR-related nodes.
- switch (node->opcode()) {
- case IrOpcode::kOsrNormalEntry:
- node->ReplaceUses(graph->NewNode(common->Dead()));
- break;
- case IrOpcode::kOsrLoopEntry:
- node->ReplaceUses(graph->start());
- break;
- default:
- break;
+ Node* osr_normal_entry = nullptr;
+ Node* osr_loop_entry = nullptr;
+ Node* osr_loop = nullptr;
+
+ for (Node* node : graph->start()->uses()) {
+ if (node->opcode() == IrOpcode::kOsrLoopEntry) {
+ osr_loop_entry = node; // found the OSR loop entry
+ } else if (node->opcode() == IrOpcode::kOsrNormalEntry) {
+ osr_normal_entry = node;
}
- for (Node* const input : node->inputs()) {
- if (!marker.Get(input)) {
- marker.Set(input, true);
- queue.push_back(input);
- }
+ }
+
+ if (osr_loop_entry == nullptr) {
+ // No OSR entry found, do nothing.
+ CHECK_NE(nullptr, osr_normal_entry);
+ return true;
+ }
+
+ for (Node* use : osr_loop_entry->uses()) {
+ if (use->opcode() == IrOpcode::kLoop) {
+ CHECK_EQ(nullptr, osr_loop); // should be only one OSR loop.
+ osr_loop = use; // found the OSR loop.
}
}
+ CHECK_NE(nullptr, osr_loop); // Should have found the OSR loop.
+
+ // Analyze the graph to determine how deeply nested the OSR loop is.
+ LoopTree* loop_tree = LoopFinder::BuildLoopTree(graph, tmp_zone);
+
+ LoopTree::Loop* loop = loop_tree->ContainingLoop(osr_loop);
+ if (loop->depth() > 0) return false; // cannot OSR inner loops yet.
+
+ // TODO(titzer): perform loop peeling or graph duplication.
+
+ // Replace the normal entry with {Dead} and the loop entry with {Start}
+ // and run the control reducer to clean up the graph.
+ osr_normal_entry->ReplaceUses(graph->NewNode(common->Dead()));
+ osr_loop_entry->ReplaceUses(graph->start());
ControlReducer::ReduceGraph(tmp_zone, jsgraph, common);
+
+ return true;
}
« no previous file with comments | « src/compiler/osr.h ('k') | src/compiler/pipeline.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698