OLD | NEW |
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "vm/flow_graph_inliner.h" | 5 #include "vm/flow_graph_inliner.h" |
6 | 6 |
7 #include "vm/compiler.h" | 7 #include "vm/compiler.h" |
8 #include "vm/flags.h" | 8 #include "vm/flags.h" |
9 #include "vm/flow_graph.h" | 9 #include "vm/flow_graph.h" |
10 #include "vm/flow_graph_builder.h" | 10 #include "vm/flow_graph_builder.h" |
(...skipping 274 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
285 GrowableArray<ClosureCallInstr*> closure_calls_; | 285 GrowableArray<ClosureCallInstr*> closure_calls_; |
286 GrowableArray<InstanceCallInfo> instance_calls_; | 286 GrowableArray<InstanceCallInfo> instance_calls_; |
287 GrowableArray<intptr_t> skip_static_call_deopt_ids_; | 287 GrowableArray<intptr_t> skip_static_call_deopt_ids_; |
288 | 288 |
289 DISALLOW_COPY_AND_ASSIGN(CallSites); | 289 DISALLOW_COPY_AND_ASSIGN(CallSites); |
290 }; | 290 }; |
291 | 291 |
292 | 292 |
293 class CallSiteInliner : public ValueObject { | 293 class CallSiteInliner : public ValueObject { |
294 public: | 294 public: |
295 CallSiteInliner(FlowGraph* flow_graph, GrowableArray<Field*>* guarded_fields) | 295 explicit CallSiteInliner(FlowGraph* flow_graph) |
296 : caller_graph_(flow_graph), | 296 : caller_graph_(flow_graph), |
297 inlined_(false), | 297 inlined_(false), |
298 initial_size_(flow_graph->InstructionCount()), | 298 initial_size_(flow_graph->InstructionCount()), |
299 inlined_size_(0), | 299 inlined_size_(0), |
300 inlining_depth_(1), | 300 inlining_depth_(1), |
301 collected_call_sites_(NULL), | 301 collected_call_sites_(NULL), |
302 inlining_call_sites_(NULL), | 302 inlining_call_sites_(NULL), |
303 function_cache_(), | 303 function_cache_() { } |
304 guarded_fields_(guarded_fields) { } | |
305 | 304 |
306 // Inlining heuristics based on Cooper et al. 2008. | 305 // Inlining heuristics based on Cooper et al. 2008. |
307 bool ShouldWeInline(intptr_t instr_count, | 306 bool ShouldWeInline(intptr_t instr_count, |
308 intptr_t call_site_count, | 307 intptr_t call_site_count, |
309 intptr_t const_arg_count) { | 308 intptr_t const_arg_count) { |
310 if (instr_count <= FLAG_inlining_size_threshold) { | 309 if (instr_count <= FLAG_inlining_size_threshold) { |
311 return true; | 310 return true; |
312 } | 311 } |
313 if (call_site_count <= FLAG_inlining_callee_call_sites_threshold) { | 312 if (call_site_count <= FLAG_inlining_callee_call_sites_threshold) { |
314 return true; | 313 return true; |
(...skipping 180 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
495 callee_graph->ComputeSSA(caller_graph_->max_virtual_register_number(), | 494 callee_graph->ComputeSSA(caller_graph_->max_virtual_register_number(), |
496 ¶m_stubs); | 495 ¶m_stubs); |
497 DEBUG_ASSERT(callee_graph->VerifyUseLists()); | 496 DEBUG_ASSERT(callee_graph->VerifyUseLists()); |
498 } | 497 } |
499 | 498 |
500 { | 499 { |
501 TimerScope timer(FLAG_compiler_stats, | 500 TimerScope timer(FLAG_compiler_stats, |
502 &CompilerStats::graphinliner_opt_timer, | 501 &CompilerStats::graphinliner_opt_timer, |
503 isolate); | 502 isolate); |
504 // TODO(zerny): Do more optimization passes on the callee graph. | 503 // TODO(zerny): Do more optimization passes on the callee graph. |
505 FlowGraphOptimizer optimizer(callee_graph, guarded_fields_); | 504 FlowGraphOptimizer optimizer(callee_graph); |
506 optimizer.ApplyICData(); | 505 optimizer.ApplyICData(); |
507 DEBUG_ASSERT(callee_graph->VerifyUseLists()); | 506 DEBUG_ASSERT(callee_graph->VerifyUseLists()); |
508 } | 507 } |
509 | 508 |
510 if (FLAG_trace_inlining && | 509 if (FLAG_trace_inlining && |
511 (FLAG_print_flow_graph || FLAG_print_flow_graph_optimized)) { | 510 (FLAG_print_flow_graph || FLAG_print_flow_graph_optimized)) { |
512 OS::Print("Callee graph for inlining %s\n", | 511 OS::Print("Callee graph for inlining %s\n", |
513 function.ToFullyQualifiedCString()); | 512 function.ToFullyQualifiedCString()); |
514 FlowGraphPrinter printer(*callee_graph); | 513 FlowGraphPrinter printer(*callee_graph); |
515 printer.PrintBlocks(); | 514 printer.PrintBlocks(); |
(...skipping 312 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
828 | 827 |
829 | 828 |
830 FlowGraph* caller_graph_; | 829 FlowGraph* caller_graph_; |
831 bool inlined_; | 830 bool inlined_; |
832 intptr_t initial_size_; | 831 intptr_t initial_size_; |
833 intptr_t inlined_size_; | 832 intptr_t inlined_size_; |
834 intptr_t inlining_depth_; | 833 intptr_t inlining_depth_; |
835 CallSites* collected_call_sites_; | 834 CallSites* collected_call_sites_; |
836 CallSites* inlining_call_sites_; | 835 CallSites* inlining_call_sites_; |
837 GrowableArray<ParsedFunction*> function_cache_; | 836 GrowableArray<ParsedFunction*> function_cache_; |
838 GrowableArray<Field*>* guarded_fields_; | |
839 | 837 |
840 DISALLOW_COPY_AND_ASSIGN(CallSiteInliner); | 838 DISALLOW_COPY_AND_ASSIGN(CallSiteInliner); |
841 }; | 839 }; |
842 | 840 |
843 | 841 |
844 void FlowGraphInliner::CollectGraphInfo(FlowGraph* flow_graph) { | 842 void FlowGraphInliner::CollectGraphInfo(FlowGraph* flow_graph) { |
845 GraphInfoCollector info; | 843 GraphInfoCollector info; |
846 info.Collect(*flow_graph); | 844 info.Collect(*flow_graph); |
847 const Function& function = flow_graph->parsed_function().function(); | 845 const Function& function = flow_graph->parsed_function().function(); |
848 function.set_optimized_instruction_count( | 846 function.set_optimized_instruction_count( |
(...skipping 20 matching lines...) Expand all Loading... |
869 flow_graph_->parsed_function().function().ToCString())); | 867 flow_graph_->parsed_function().function().ToCString())); |
870 | 868 |
871 if (FLAG_trace_inlining && | 869 if (FLAG_trace_inlining && |
872 (FLAG_print_flow_graph || FLAG_print_flow_graph_optimized)) { | 870 (FLAG_print_flow_graph || FLAG_print_flow_graph_optimized)) { |
873 OS::Print("Before Inlining of %s\n", flow_graph_-> | 871 OS::Print("Before Inlining of %s\n", flow_graph_-> |
874 parsed_function().function().ToFullyQualifiedCString()); | 872 parsed_function().function().ToFullyQualifiedCString()); |
875 FlowGraphPrinter printer(*flow_graph_); | 873 FlowGraphPrinter printer(*flow_graph_); |
876 printer.PrintBlocks(); | 874 printer.PrintBlocks(); |
877 } | 875 } |
878 | 876 |
879 CallSiteInliner inliner(flow_graph_, guarded_fields_); | 877 CallSiteInliner inliner(flow_graph_); |
880 inliner.InlineCalls(); | 878 inliner.InlineCalls(); |
881 | 879 |
882 if (inliner.inlined()) { | 880 if (inliner.inlined()) { |
883 flow_graph_->RepairGraphAfterInlining(); | 881 flow_graph_->RepairGraphAfterInlining(); |
884 if (FLAG_trace_inlining) { | 882 if (FLAG_trace_inlining) { |
885 OS::Print("Inlining growth factor: %f\n", inliner.GrowthFactor()); | 883 OS::Print("Inlining growth factor: %f\n", inliner.GrowthFactor()); |
886 if (FLAG_print_flow_graph || FLAG_print_flow_graph_optimized) { | 884 if (FLAG_print_flow_graph || FLAG_print_flow_graph_optimized) { |
887 OS::Print("After Inlining of %s\n", flow_graph_-> | 885 OS::Print("After Inlining of %s\n", flow_graph_-> |
888 parsed_function().function().ToFullyQualifiedCString()); | 886 parsed_function().function().ToFullyQualifiedCString()); |
889 FlowGraphPrinter printer(*flow_graph_); | 887 FlowGraphPrinter printer(*flow_graph_); |
890 printer.PrintBlocks(); | 888 printer.PrintBlocks(); |
891 } | 889 } |
892 } | 890 } |
893 } | 891 } |
894 } | 892 } |
895 | 893 |
896 } // namespace dart | 894 } // namespace dart |
OLD | NEW |