• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /**
2  * Copyright 2021-2023 Huawei Technologies Co., Ltd
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 #include "backend/common/optimizer/common_backend_optimization.h"
17 #include <memory>
18 #include <string>
19 #include "include/backend/optimizer/optimizer.h"
20 #include "backend/common/pass/convert_list_to_tuple.h"
21 #include "backend/common/pass/eliminate_func_data_type.h"
22 #include "backend/common/pass/convert_const_input_to_attr.h"
23 #include "backend/common/pass/add_input_structural_for_py_execute.h"
24 #include "backend/common/pass/custom_op_const_input_to_attr.h"
25 #include "backend/common/pass/custom_op_reg_info_to_attr.h"
26 #include "backend/common/pass/convert_tuple_output_to_maketuple.h"
27 #include "backend/common/pass/convert_const_input_to_tensor_input.h"
28 #include "backend/common/pass/convert_tuple_input_to_dynamic_input.h"
29 #include "backend/common/pass/convert_const_scalar_to_tensor.h"
30 #include "backend/common/pass/convert_attr_to_unify_mindir.h"
31 #include "backend/common/pass/optimize_updatestate.h"
32 #include "backend/common/pass/conv_transpose_to_conv_bp.h"
33 #include "backend/common/pass/add_dynamic_shape_attr.h"
34 #include "backend/common/pass/add_akg_kernel_attrs.h"
35 #include "backend/common/pass/inplace_assign_for_custom_op.h"
36 #include "backend/common/pass/flatten_concat_fission.h"
37 #include "backend/common/optimizer/dynamic_shape/convert_custom_op.h"
38 #include "backend/common/optimizer/dynamic_shape/link_custom_op.h"
39 #include "backend/common/pass/convert_unused_tuple_para_to_make_tuple.h"
40 #include "backend/common/pass/convert_dynamic_broadcast_to.h"
41 #include "backend/common/pass/broadcast_to_fusion.h"
42 #include "backend/common/pass/add_attr_to_node/add_attr_to_node.h"
43 #include "backend/common/pass/replace_addn_fusion.h"
44 #include "utils/ms_context.h"
45 #include "include/common/debug/anf_ir_dump.h"
46 #ifdef ENABLE_DUMP_IR
47 #include "include/backend/debug/data_dump/dump_json_parser.h"
48 #include "include/backend/debug/data_dump/dump_utils.h"
49 #include "include/backend/debug/debugger/proto_exporter.h"
50 #include "backend/common/session/session_basic.h"
51 #endif
52 
53 namespace mindspore {
54 namespace opt {
GetBackendCommonOptimizationPassManagerPtr(const FuncGraphPtr & graph)55 PassManagerPtr GetBackendCommonOptimizationPassManagerPtr(const FuncGraphPtr &graph) {
56   auto common_pm = std::make_shared<PassManager>("common_pm");
57   common_pm->AddPass(std::make_shared<ConvertDynamicBroadcastTo>());
58   common_pm->AddPass(std::make_shared<ConvertConstInputToAttr>());
59   common_pm->AddPass(std::make_shared<CustomOpConstInputToAttr>());
60   // Disable const to tensor pass, ascend platform need to match the change in the future.
61   auto context = MsContext::GetInstance();
62   int execution_mode = context->get_param<int>(MS_CTX_EXECUTION_MODE);
63   if (execution_mode == kPynativeMode) {
64     common_pm->AddPass(std::make_shared<ConvertConstInputToTensorInput>());
65   }
66   common_pm->AddPass(std::make_shared<ConvertConstInputToTensorInputForPrint>());
67   common_pm->AddPass(std::make_shared<ConvertTupleOutputToMaketuple>());
68   common_pm->AddPass(std::make_shared<ConvertUnusedTupleParaToMakeTuple>());
69   common_pm->AddPass(std::make_shared<FlattenConcatFission>());
70   common_pm->AddPass(std::make_shared<AddInputStructuralForPyExecute>());
71   common_pm->AddPass(std::make_shared<BroadcastToFusion>());
72   common_pm->AddPass(std::make_shared<AddAttrToNode>());
73   common_pm->AddPass(std::make_shared<ReplaceAddNFusion>());
74   return common_pm;
75 }
76 
BackendCommonOptimization(const std::shared_ptr<session::KernelGraph> & kernel_graph)77 void BackendCommonOptimization(const std::shared_ptr<session::KernelGraph> &kernel_graph) {
78   PROF_START(backend_common_optimization);
79   MS_EXCEPTION_IF_NULL(kernel_graph);
80   MS_LOG(INFO) << "Status record: start common optimization. graph id: " << kernel_graph->graph_id();
81 #ifdef ENABLE_DUMP_IR
82   auto context_ptr = MsContext::GetInstance();
83   MS_EXCEPTION_IF_NULL(context_ptr);
84   if (context_ptr->CanDump(kIntroductory)) {
85     std::string file_name = "hwopt_common_before_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
86     DumpIR(file_name, kernel_graph);
87   }
88 #endif
89   auto optimizer = std::make_shared<GraphOptimizer>();
90   optimizer->AddPassManager(GetBackendCommonOptimizationPassManagerPtr(kernel_graph));
91   (void)optimizer->Optimize(kernel_graph);
92   kernel_graph->SetExecOrderByDefault();
93   PROF_END(backend_common_optimization);
94 #ifdef ENABLE_DUMP_IR
95   if (context_ptr->CanDump(kIntroductory)) {
96     std::string file_name = "hwopt_common_after_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
97     DumpIR(file_name, kernel_graph);
98   }
99 #endif
100   MS_LOG(INFO) << "Status record: end common optimization. graph id: " << kernel_graph->graph_id();
101 }
102 
103 // Delete this optimizer when dynamic and static ReduceSum is unified.
OpBackendCommonOptimization(const std::shared_ptr<session::KernelGraph> & kernel_graph)104 void OpBackendCommonOptimization(const std::shared_ptr<session::KernelGraph> &kernel_graph) {
105   MS_EXCEPTION_IF_NULL(kernel_graph);
106   MS_LOG(INFO) << "Status record: start op common optimization. graph id: " << kernel_graph->graph_id();
107   auto optimizer = std::make_shared<GraphOptimizer>();
108   auto common_pm = std::make_shared<PassManager>("op_common_pm");
109   common_pm->AddPass(std::make_shared<ConvertConstInputToTensorInputForPrint>());
110   common_pm->AddPass(std::make_shared<BroadcastToFusion>());
111   common_pm->AddPass(std::make_shared<AddAttrToNode>());
112   optimizer->AddPassManager(common_pm);
113   (void)optimizer->Optimize(kernel_graph);
114   kernel_graph->SetExecOrderByDefault();
115   MS_LOG(INFO) << "Status record: end op common optimization. graph id: " << kernel_graph->graph_id();
116 }
117 
CommonFinalOptimization(const std::shared_ptr<session::KernelGraph> & kernel_graph)118 void CommonFinalOptimization(const std::shared_ptr<session::KernelGraph> &kernel_graph) {
119   MS_EXCEPTION_IF_NULL(kernel_graph);
120   // Run optimizer passes.
121   auto optimizer = std::make_shared<GraphOptimizer>();
122   auto pm = std::make_shared<PassManager>("final_opt");
123   pm->AddPass(std::make_shared<OptimizeUpdateState>());
124   pm->AddPass(std::make_shared<AddAkgKernelAttrs>());
125   optimizer->AddPassManager(pm);
126   (void)optimizer->Optimize(kernel_graph);
127   kernel_graph->SetExecOrderByDefault();
128 #ifdef ENABLE_DUMP_IR
129   // Dump IR if save_graphs is set.
130   auto context = MsContext::GetInstance();
131   MS_EXCEPTION_IF_NULL(context);
132   if (context->CanDump(kIntroductory)) {
133     std::string filename = "hwopt_common_final_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
134     DumpIR(filename, kernel_graph);
135   }
136 #endif
137 }
138 
GetCommonUnifyMindIRPassManager()139 PassManagerPtr GetCommonUnifyMindIRPassManager() {
140   auto pm = std::make_shared<PassManager>("common_unify_mindir_pm");
141   pm->AddPass(std::make_shared<ConvTransposeToConvBackpropInputPass>());
142   pm->AddPass(std::make_shared<CustomOpRegInfoToAttr>());
143   pm->AddPass(std::make_shared<InplaceAssignForCustomOp>());
144   pm->AddPass(std::make_shared<ConvertAttrToUnifyMindIR>());
145   return pm;
146 }
147 
CommonUnifyMindIR(const std::shared_ptr<session::KernelGraph> & kernel_graph)148 void CommonUnifyMindIR(const std::shared_ptr<session::KernelGraph> &kernel_graph) {
149   MS_EXCEPTION_IF_NULL(kernel_graph);
150   MS_LOG(INFO) << "start common unify mindir opt graph:" << kernel_graph->graph_id();
151 #ifdef ENABLE_DUMP_IR
152   auto context_ptr = MsContext::GetInstance();
153   MS_EXCEPTION_IF_NULL(context_ptr);
154   if (context_ptr->CanDump(kIntroductory)) {
155     std::string file_name =
156       "hwopt_common_unify_mindir_before_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
157     DumpIR(file_name, kernel_graph);
158   }
159 #endif
160   auto opt = std::make_shared<GraphOptimizer>();
161   opt->AddPassManager(GetCommonUnifyMindIRPassManager());
162   (void)opt->Optimize(kernel_graph);
163   kernel_graph->SetExecOrderByDefault();
164 #ifdef ENABLE_DUMP_IR
165   if (context_ptr->CanDump(kIntroductory)) {
166     std::string file_name = "hwopt_common_unify_mindir_after_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
167     DumpIR(file_name, kernel_graph);
168   }
169 #endif
170 }
171 
AddDynamicShapeAttrPass(const std::shared_ptr<session::KernelGraph> & kernel_graph)172 void AddDynamicShapeAttrPass(const std::shared_ptr<session::KernelGraph> &kernel_graph) {
173   auto opt = std::make_shared<GraphOptimizer>();
174   auto pm = std::make_shared<PassManager>("add_dynamic_shape_attr");
175   pm->AddPass(std::make_shared<AddDynamicShapeAttr>());
176   opt->AddPassManager(pm);
177   (void)opt->Optimize(kernel_graph);
178 }
179 
GetEliminateIllegalDataTypePassManager()180 PassManagerPtr GetEliminateIllegalDataTypePassManager() {
181   auto pm = std::make_shared<PassManager>("common_eliminate_illegal_data_type_pm");
182   pm->AddPass(std::make_shared<ConvertListToTuple>("convert_list_to_tuple"));
183   pm->AddPass(std::make_shared<EliminateFuncDataType>());
184   return pm;
185 }
186 
EliminateIllegalDataTypePass(const std::shared_ptr<session::KernelGraph> & kernel_graph)187 void EliminateIllegalDataTypePass(const std::shared_ptr<session::KernelGraph> &kernel_graph) {
188   MS_EXCEPTION_IF_NULL(kernel_graph);
189   MS_LOG(INFO) << "Start eliminate illegal data type for kernel graph id:" << kernel_graph->graph_id();
190 #ifdef ENABLE_DUMP_IR
191   auto context_ptr = MsContext::GetInstance();
192   MS_EXCEPTION_IF_NULL(context_ptr);
193   if (context_ptr->CanDump(kIntroductory)) {
194     std::string file_name =
195       "hwopt_common_eliminate_illegal_data_type_before_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
196     DumpIR(file_name, kernel_graph);
197   }
198 #endif
199   auto opt = std::make_shared<GraphOptimizer>();
200   opt->AddPassManager(GetEliminateIllegalDataTypePassManager());
201   (void)opt->Optimize(kernel_graph);
202   kernel_graph->SetExecOrderByDefault();
203 #ifdef ENABLE_DUMP_IR
204   if (context_ptr->CanDump(kIntroductory)) {
205     std::string file_name =
206       "hwopt_common_eliminate_illegal_data_type_after_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
207     DumpIR(file_name, kernel_graph);
208   }
209 #endif
210 }
211 
DynamicShapeConvertPass(const std::shared_ptr<session::KernelGraph> & kernel_graph)212 void DynamicShapeConvertPass(const std::shared_ptr<session::KernelGraph> &kernel_graph) {
213   MS_EXCEPTION_IF_NULL(kernel_graph);
214   MS_LOG(INFO) << "Start dynamic shape convert for kernel graph id:" << kernel_graph->graph_id();
215 #ifdef ENABLE_DUMP_IR
216   auto context_ptr = MsContext::GetInstance();
217   MS_EXCEPTION_IF_NULL(context_ptr);
218   if (context_ptr->CanDump(kIntroductory)) {
219     std::string file_name =
220       "hwopt_d_before_dynamic_shape_convert_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
221     DumpIR(file_name, kernel_graph);
222   }
223 #endif
224   auto optimizer = std::make_shared<opt::GraphOptimizer>();
225   auto dynamic_shape_convert_pm = std::make_shared<opt::PassManager>("dynamic_shape_convert_pm");
226   dynamic_shape_convert_pm->AddPass(std::make_shared<opt::dynamic_shape::ConvertCustomOp>());
227   dynamic_shape_convert_pm->AddPass(std::make_shared<opt::dynamic_shape::LinkCustomOp>());
228   optimizer->AddPassManager(dynamic_shape_convert_pm);
229   (void)optimizer->Optimize(kernel_graph);
230 #ifdef ENABLE_DUMP_IR
231   if (context_ptr->CanDump(kIntroductory)) {
232     std::string file_name =
233       "hwopt_d_after_dynamic_shape_convert_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
234     DumpIR(file_name, kernel_graph);
235   }
236 #endif
237 }
238 
OptimizationWithoutBackend(const std::shared_ptr<session::KernelGraph> & kernel_graph)239 void OptimizationWithoutBackend(const std::shared_ptr<session::KernelGraph> &kernel_graph) {
240   MS_EXCEPTION_IF_NULL(kernel_graph);
241   MS_LOG(DEBUG) << "Start OptimizationWithoutBackend for kernel graph id:" << kernel_graph->graph_id();
242 #ifdef ENABLE_DUMP_IR
243   auto context_ptr = MsContext::GetInstance();
244   MS_EXCEPTION_IF_NULL(context_ptr);
245   if (context_ptr->CanDump(kIntroductory)) {
246     std::string file_name =
247       "hwopt_d_before_optimization_without_backend_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
248     DumpIR(file_name, kernel_graph);
249   }
250 #endif
251   EliminateIllegalDataTypePass(kernel_graph);
252   CommonUnifyMindIR(kernel_graph);
253   BackendCommonOptimization(kernel_graph);
254   MS_LOG(DEBUG) << "End OptimizationWithoutBackend for kernel graph id:" << kernel_graph->graph_id();
255 #ifdef ENABLE_DUMP_IR
256   if (context_ptr->CanDump(kIntroductory)) {
257     std::string file_name =
258       "hwopt_d_after_optimization_without_backend_graph_" + std::to_string(kernel_graph->graph_id()) + ".ir";
259     DumpIR(file_name, kernel_graph);
260   }
261 #endif
262 }
263 
OptimizationForAnyTypeKernelGraph(const std::shared_ptr<session::KernelGraph> & kernel_graph)264 void OptimizationForAnyTypeKernelGraph(const std::shared_ptr<session::KernelGraph> &kernel_graph) {
265   MS_EXCEPTION_IF_NULL(kernel_graph);
266   auto common_pm = std::make_shared<opt::PassManager>("common_pm");
267   common_pm->AddPass(std::make_shared<ConvertListToTuple>("convert_list_to_tuple"));
268   common_pm->AddPass(std::make_shared<EliminateFuncDataType>());
269   common_pm->AddPass(std::make_shared<ConvertConstInputToAttr>());
270   common_pm->AddPass(std::make_shared<opt::ConvertConstInputToTensorInputForPrint>());
271   common_pm->AddPass(std::make_shared<opt::ConvertTupleOutputToMaketuple>());
272   auto optimizer = std::make_shared<opt::GraphOptimizer>();
273   optimizer->AddPassManager(common_pm);
274   optimizer->Optimize(kernel_graph);
275 }
276 }  // namespace opt
277 }  // namespace mindspore
278