| 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/block_scheduler.h" | 7 #include "vm/block_scheduler.h" |
| 8 #include "vm/compiler.h" | 8 #include "vm/compiler.h" |
| 9 #include "vm/flags.h" | 9 #include "vm/flags.h" |
| 10 #include "vm/flow_graph.h" | 10 #include "vm/flow_graph.h" |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 54 "Inline recursive function calls up to threshold recursion depth."); | 54 "Inline recursive function calls up to threshold recursion depth."); |
| 55 DEFINE_FLAG(int, max_inlined_per_depth, 500, | 55 DEFINE_FLAG(int, max_inlined_per_depth, 500, |
| 56 "Max. number of inlined calls per depth"); | 56 "Max. number of inlined calls per depth"); |
| 57 DEFINE_FLAG(bool, print_inlining_tree, false, "Print inlining tree"); | 57 DEFINE_FLAG(bool, print_inlining_tree, false, "Print inlining tree"); |
| 58 DEFINE_FLAG(bool, enable_inlining_annotations, false, | 58 DEFINE_FLAG(bool, enable_inlining_annotations, false, |
| 59 "Enable inlining annotations"); | 59 "Enable inlining annotations"); |
| 60 | 60 |
| 61 DECLARE_FLAG(bool, compiler_stats); | 61 DECLARE_FLAG(bool, compiler_stats); |
| 62 DECLARE_FLAG(int, max_deoptimization_counter_threshold); | 62 DECLARE_FLAG(int, max_deoptimization_counter_threshold); |
| 63 DECLARE_FLAG(bool, polymorphic_with_deopt); | 63 DECLARE_FLAG(bool, polymorphic_with_deopt); |
| 64 DECLARE_FLAG(bool, precompilation); |
| 64 DECLARE_FLAG(bool, print_flow_graph); | 65 DECLARE_FLAG(bool, print_flow_graph); |
| 65 DECLARE_FLAG(bool, print_flow_graph_optimized); | 66 DECLARE_FLAG(bool, print_flow_graph_optimized); |
| 66 DECLARE_FLAG(bool, verify_compiler); | 67 DECLARE_FLAG(bool, verify_compiler); |
| 67 | 68 |
| 68 // Quick access to the current zone. | 69 // Quick access to the current zone. |
| 69 #define Z (zone()) | 70 #define Z (zone()) |
| 70 | 71 |
| 71 #define TRACE_INLINING(statement) \ | 72 #define TRACE_INLINING(statement) \ |
| 72 do { \ | 73 do { \ |
| 73 if (trace_inlining()) statement; \ | 74 if (trace_inlining()) statement; \ |
| (...skipping 548 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 622 // Abort if the inlinable bit on the function is low. | 623 // Abort if the inlinable bit on the function is low. |
| 623 if (!function.CanBeInlined()) { | 624 if (!function.CanBeInlined()) { |
| 624 TRACE_INLINING(THR_Print(" Bailout: not inlinable\n")); | 625 TRACE_INLINING(THR_Print(" Bailout: not inlinable\n")); |
| 625 PRINT_INLINING_TREE("Not inlinable", | 626 PRINT_INLINING_TREE("Not inlinable", |
| 626 &call_data->caller, &function, call_data->call); | 627 &call_data->caller, &function, call_data->call); |
| 627 return false; | 628 return false; |
| 628 } | 629 } |
| 629 | 630 |
| 630 // Function has no type feedback. With precompilation we don't rely on | 631 // Function has no type feedback. With precompilation we don't rely on |
| 631 // type feedback. | 632 // type feedback. |
| 632 if (!Compiler::always_optimize() && | 633 if (!FLAG_precompilation && |
| 633 function.ic_data_array() == Object::null()) { | 634 function.ic_data_array() == Object::null()) { |
| 634 TRACE_INLINING(THR_Print(" Bailout: not compiled yet\n")); | 635 TRACE_INLINING(THR_Print(" Bailout: not compiled yet\n")); |
| 635 PRINT_INLINING_TREE("Not compiled", | 636 PRINT_INLINING_TREE("Not compiled", |
| 636 &call_data->caller, &function, call_data->call); | 637 &call_data->caller, &function, call_data->call); |
| 637 return false; | 638 return false; |
| 638 } | 639 } |
| 639 | 640 |
| 640 // Abort if this function has deoptimized too much. | 641 // Abort if this function has deoptimized too much. |
| 641 if (function.deoptimization_counter() >= | 642 if (function.deoptimization_counter() >= |
| 642 FLAG_max_deoptimization_counter_threshold) { | 643 FLAG_max_deoptimization_counter_threshold) { |
| (...skipping 136 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 779 DEBUG_ASSERT(callee_graph->VerifyUseLists()); | 780 DEBUG_ASSERT(callee_graph->VerifyUseLists()); |
| 780 } | 781 } |
| 781 | 782 |
| 782 { | 783 { |
| 783 CSTAT_TIMER_SCOPE(thread(), graphinliner_opt_timer); | 784 CSTAT_TIMER_SCOPE(thread(), graphinliner_opt_timer); |
| 784 // TODO(fschneider): Improve suppression of speculative inlining. | 785 // TODO(fschneider): Improve suppression of speculative inlining. |
| 785 // Deopt-ids overlap between caller and callee. | 786 // Deopt-ids overlap between caller and callee. |
| 786 FlowGraphOptimizer optimizer(callee_graph, | 787 FlowGraphOptimizer optimizer(callee_graph, |
| 787 inliner_->use_speculative_inlining_, | 788 inliner_->use_speculative_inlining_, |
| 788 inliner_->inlining_black_list_); | 789 inliner_->inlining_black_list_); |
| 789 if (Compiler::always_optimize()) { | 790 if (FLAG_precompilation) { |
| 790 optimizer.PopulateWithICData(); | 791 optimizer.PopulateWithICData(); |
| 791 | 792 |
| 792 optimizer.ApplyClassIds(); | 793 optimizer.ApplyClassIds(); |
| 793 DEBUG_ASSERT(callee_graph->VerifyUseLists()); | 794 DEBUG_ASSERT(callee_graph->VerifyUseLists()); |
| 794 | 795 |
| 795 FlowGraphTypePropagator::Propagate(callee_graph); | 796 FlowGraphTypePropagator::Propagate(callee_graph); |
| 796 DEBUG_ASSERT(callee_graph->VerifyUseLists()); | 797 DEBUG_ASSERT(callee_graph->VerifyUseLists()); |
| 797 } | 798 } |
| 798 optimizer.ApplyICData(); | 799 optimizer.ApplyICData(); |
| 799 DEBUG_ASSERT(callee_graph->VerifyUseLists()); | 800 DEBUG_ASSERT(callee_graph->VerifyUseLists()); |
| (...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 906 return false; | 907 return false; |
| 907 } else { | 908 } else { |
| 908 // Fall through to exit long jump scope. | 909 // Fall through to exit long jump scope. |
| 909 } | 910 } |
| 910 } | 911 } |
| 911 } | 912 } |
| 912 | 913 |
| 913 // Propagate a compile-time error. Only in precompilation do we attempt to | 914 // Propagate a compile-time error. Only in precompilation do we attempt to |
| 914 // inline functions that have never been compiled before; when JITing we | 915 // inline functions that have never been compiled before; when JITing we |
| 915 // should only see compile-time errors in unoptimized compilation. | 916 // should only see compile-time errors in unoptimized compilation. |
| 916 ASSERT(Compiler::always_optimize()); | 917 ASSERT(FLAG_precompilation); |
| 917 Thread::Current()->long_jump_base()->Jump(1, error); | 918 Thread::Current()->long_jump_base()->Jump(1, error); |
| 918 UNREACHABLE(); | 919 UNREACHABLE(); |
| 919 return false; | 920 return false; |
| 920 } | 921 } |
| 921 | 922 |
| 922 void PrintInlinedInfo(const Function& top) { | 923 void PrintInlinedInfo(const Function& top) { |
| 923 if (inlined_info_.length() > 0) { | 924 if (inlined_info_.length() > 0) { |
| 924 THR_Print("Inlining into: '%s' growth: %f (%" Pd " -> %" Pd ")\n", | 925 THR_Print("Inlining into: '%s' growth: %f (%" Pd " -> %" Pd ")\n", |
| 925 top.ToFullyQualifiedCString(), | 926 top.ToFullyQualifiedCString(), |
| 926 GrowthFactor(), | 927 GrowthFactor(), |
| (...skipping 1007 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1934 intptr_t FlowGraphInliner::NextInlineId(const Function& function, | 1935 intptr_t FlowGraphInliner::NextInlineId(const Function& function, |
| 1935 intptr_t parent_id) { | 1936 intptr_t parent_id) { |
| 1936 const intptr_t id = inline_id_to_function_->length(); | 1937 const intptr_t id = inline_id_to_function_->length(); |
| 1937 inline_id_to_function_->Add(&function); | 1938 inline_id_to_function_->Add(&function); |
| 1938 caller_inline_id_->Add(parent_id); | 1939 caller_inline_id_->Add(parent_id); |
| 1939 return id; | 1940 return id; |
| 1940 } | 1941 } |
| 1941 | 1942 |
| 1942 | 1943 |
| 1943 } // namespace dart | 1944 } // namespace dart |
| OLD | NEW |