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

Unified Diff: runtime/vm/flow_graph.cc

Issue 10893027: Inlining of static calls with trivial function bodies. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 8 years, 4 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 | « runtime/vm/flow_graph.h ('k') | runtime/vm/flow_graph_builder.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: runtime/vm/flow_graph.cc
diff --git a/runtime/vm/flow_graph.cc b/runtime/vm/flow_graph.cc
index 9f2abd0067f31a14c83316fd36f8e354255b2fa1..d1135df86d4ed3a80fc0747fab14cc74ba46756f 100644
--- a/runtime/vm/flow_graph.cc
+++ b/runtime/vm/flow_graph.cc
@@ -8,6 +8,7 @@
#include "vm/flow_graph_builder.h"
#include "vm/intermediate_language.h"
#include "vm/longjump.h"
+#include "vm/growable_array.h"
namespace dart {
@@ -23,7 +24,8 @@ FlowGraph::FlowGraph(const FlowGraphBuilder& builder,
graph_entry_(graph_entry),
preorder_(),
postorder_(),
- reverse_postorder_() {
+ reverse_postorder_(),
+ exits_(NULL) {
DiscoverBlocks();
}
@@ -292,7 +294,8 @@ void FlowGraph::ComputeUseLists() {
}
-void FlowGraph::ComputeSSA() {
+void FlowGraph::ComputeSSA(intptr_t next_virtual_register_number) {
+ current_ssa_temp_index_ = next_virtual_register_number;
GrowableArray<BitVector*> dominance_frontier;
ComputeDominators(&preorder_, &parent_, &dominance_frontier);
InsertPhis(preorder_, assigned_vars_, dominance_frontier);
@@ -680,4 +683,70 @@ void FlowGraph::Bailout(const char* reason) const {
}
+// Helper to get the block-entry of an instruction.
+static BlockEntryInstr* GetBlockEntry(Instruction* instr) {
+ while (!instr->IsBlockEntry()) instr = instr->previous();
+ return instr->AsBlockEntry();
+}
+
+
+// Helper to link two instructions in the graph.
+static void Link(Instruction* prev, Instruction* next) {
+ ASSERT(prev != next);
+ prev->set_next(next);
+ next->set_previous(prev);
+}
+
+
+// Inline a flow graph at a call site.
+//
+// Assumes the callee graph was computed with BuildGraphForInlining and
+// transformed to SSA with ComputeSSAForInlining, and that the use lists have
+// been correctly computed.
+//
+// After inlining the caller graph will correctly have adjusted the pre/post
+// orders, the dominator tree and the use lists.
+void FlowGraph::InlineCall(BindInstr* caller_instr,
+ StaticCallComp* caller_comp,
+ FlowGraph* callee_graph) {
+ ASSERT(callee_graph->exits() != NULL);
+ ASSERT(callee_graph->graph_entry()->SuccessorCount() == 1);
+ ASSERT(callee_graph->max_virtual_register_number() >
+ max_virtual_register_number());
+
+ // TODO(zerny): Implement support for callee graphs with control flow.
+ ASSERT(callee_graph->preorder().length() == 2);
+
+ // Adjust the SSA temp index by the callee graph's index.
+ current_ssa_temp_index_ = callee_graph->max_virtual_register_number();
+
+ TargetEntryInstr* callee_entry = callee_graph->graph_entry()->normal_entry();
+ ZoneGrowableArray<ReturnInstr*>* callee_exits = callee_graph->exits();
+
+ // 1. Insert the callee graph into the caller graph.
+ if (callee_exits->length() == 1) {
+ ReturnInstr* exit = (*callee_exits)[0];
+ // TODO(zerny): Support one exit graph containing control flow.
+ ASSERT(callee_entry == GetBlockEntry(exit));
+ // For just one exit, replace the uses and remove the call from the graph.
+ caller_instr->ReplaceUsesWith(exit->value()->AsUse()->definition());
+ Link(caller_instr->previous(), callee_entry->next());
+ Link(exit->previous(), caller_instr->next());
+ } else {
+ // TODO(zerny): Support multiple exits.
+ UNREACHABLE();
+ }
+
+ // TODO(zerny): Adjust pre/post orders.
+ // TODO(zerny): Update dominator tree.
+
+ // Remove original arguments to the call.
+ for (intptr_t i = 0; i < caller_comp->ArgumentCount(); ++i) {
+ PushArgumentInstr* push = caller_comp->ArgumentAt(i);
+ push->ReplaceUsesWith(push->value()->AsUse()->definition());
+ push->RemoveFromGraph();
+ }
+}
+
+
} // namespace dart
« no previous file with comments | « runtime/vm/flow_graph.h ('k') | runtime/vm/flow_graph_builder.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698