1 /** 2 * Copyright 2021 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 17 #ifndef MINDSPORE_LITE_SRC_LITE_MINDRT_H_ 18 #define MINDSPORE_LITE_SRC_LITE_MINDRT_H_ 19 #include <vector> 20 #include <memory> 21 #include <string> 22 #include <unordered_map> 23 #include "actor/op_actor.h" 24 #include "src/lite_kernel.h" 25 #include "actor/actor.h" 26 #include "async/uuid_base.h" 27 #include "async/future.h" 28 #include "src/sub_graph_kernel.h" 29 #include "src/cpu_info.h" 30 #ifndef CONTROLFLOW_TENSORLIST_CLIP 31 #include "src/tensorlist.h" 32 #endif 33 34 namespace mindspore::lite { 35 36 typedef enum { GRAPH, OP_BY_OP } MindRTMode; 37 const constexpr int kSwitchMaxInputKernelSize = 3; 38 const constexpr int kSwitchMinInputKernelSize = 2; 39 const constexpr int kSwitchTruePartialInputIndex = 1; 40 const constexpr int kSwitchFalsePartialInputIndex = 2; 41 const constexpr int kSwitchMinInputTensorSize = 3; 42 const constexpr int kSwitchCondTensorIndex = 0; 43 44 class LiteOpActor : public OpActor<lite::Tensor> { 45 public: LiteOpActor(kernel::LiteKernel * kernel)46 explicit LiteOpActor(kernel::LiteKernel *kernel) : OpActor<lite::Tensor>(kernel->name()), kernel_(kernel) { 47 inputs_data_.resize(kernel_->in_tensors().size()); 48 #if defined(ENABLE_ARM) && defined(ENABLE_FP16) 49 CpuInfo cpu_info; 50 support_fp16_ = cpu_info.ArmIsSupportFp16(); 51 #endif 52 } ~LiteOpActor()53 ~LiteOpActor() override { 54 for (auto map : isolate_input_map_) { 55 auto isolate_input_tensor = map.first; 56 isolate_input_tensor->set_data(nullptr); 57 delete isolate_input_tensor; 58 } 59 delete call_node_; 60 delete partial_node_; 61 } 62 void RunOpData(OpData<lite::Tensor> *input_data, OpContext<lite::Tensor> *context = nullptr) override; 63 virtual int CompileArrow(); RunKernel(const KernelCallBack & before,const KernelCallBack & after)64 int RunKernel(const KernelCallBack &before, const KernelCallBack &after) { 65 auto ret = kernel_->Execute(before, after); 66 if (RET_OK != ret) { 67 MS_LOG(ERROR) << "run kernel failed, name: " << kernel_->name(); 68 return ret; 69 } 70 return ret; 71 } 72 int LiteActorInit(std::vector<std::shared_ptr<LiteOpActor>> *actors); 73 int ResizeGraphInput(const std::vector<mindspore::tensor::MSTensor *> &inputs, 74 const std::vector<std::vector<int>> &dims); 75 76 public: 77 void AddResultIndex(size_t index); SetSubgraphAIDMap(const std::unordered_map<kernel::LiteKernel *,AID> & partial_map)78 void SetSubgraphAIDMap(const std::unordered_map<kernel::LiteKernel *, AID> &partial_map) { 79 subgraph_to_actor_ = partial_map; 80 } 81 82 protected: 83 void SetInputShape(); 84 int InitInputData(); 85 void SetOutputData(OpContext<Tensor> *context); 86 void AsyncOutput(OpContext<Tensor> *context); 87 int CompileArrowThroughPartialCall(); 88 int CompileArrowThroughOutputKernels(); 89 virtual int PrepareOutputData(); 90 91 kernel::LiteKernel *kernel_; 92 std::vector<size_t> results_index_{}; 93 std::unordered_map<kernel::LiteKernel *, AID> subgraph_to_actor_{}; 94 std::vector<OpDataPtr<Tensor>> outputs_data_{}; 95 std::vector<Tensor *> inputs_data_{}; 96 std::unordered_map<Tensor *, Tensor *> isolate_input_map_{}; /* <calculate-tensor, src-input-tensor> */ 97 98 private: 99 void ReplaceNodeInTensor(kernel::LiteKernel *kernel, Tensor *old_tensor, Tensor *new_tensor); 100 int IsolateInputData(std::vector<std::shared_ptr<LiteOpActor>> *actors); 101 void MoveTensorInputData(Tensor *dst_tensor, Tensor *src_tensor); 102 void MoveInputData(Tensor *dst_tensor, Tensor *src_tensor); 103 void SetInputData(Tensor *dst_tensor, Tensor *src_tensor); 104 int CastInputData(Tensor *dst_tensor, Tensor *src_tensor); 105 bool NeedCastData(Tensor *dst_tensor, Tensor *src_tensor); 106 int CastTensorInputData(Tensor *dst_tensor, Tensor *src_tensor); 107 #ifndef CONTROLFLOW_TENSORLIST_CLIP 108 void MoveTensorListInputData(TensorList *dst_tensor, TensorList *src_tensor); 109 int CastTensorListInputData(TensorList *dst_tensor, TensorList *src_tensor); 110 #endif 111 112 private: 113 kernel::LiteKernel *partial_node_ = nullptr; 114 kernel::LiteKernel *call_node_ = nullptr; 115 #if defined(ENABLE_ARM) && defined(ENABLE_FP16) 116 bool support_fp16_ = false; 117 #endif 118 }; 119 120 #ifndef CONTROLFLOW_TENSORLIST_CLIP 121 class LiteSwitchOpActor : public LiteOpActor { 122 public: LiteSwitchOpActor(kernel::LiteKernel * kernel)123 explicit LiteSwitchOpActor(kernel::LiteKernel *kernel) : LiteOpActor(kernel) {} ~LiteSwitchOpActor()124 ~LiteSwitchOpActor() override { 125 delete call_node_; 126 delete switch_node_; 127 delete true_partial_node_; 128 delete false_partial_node_; 129 }; 130 void RunOpData(OpData<Tensor> *inputs, OpContext<Tensor> *context = nullptr) override; 131 int CompileArrow() override; 132 int PrepareOutputData() override; 133 134 private: 135 void AsyncTrueBranchOutput(OpContext<Tensor> *context); 136 void AsyncFalseBranchOutput(OpContext<Tensor> *context); 137 void DecreaseTrueBranchInputTensor(); 138 void DecreaseFalseBranchInputTensor(); 139 int GetSwitchAndCallNode(kernel::SubGraphKernel *subgraph_kernel); 140 void AppendOutputTensors(); 141 int CompileTrueBranchArrow(); 142 int CompileFalseBranchArrow(); 143 int CompileArrowThroughSwitchCall(); 144 145 std::vector<DataArrowPtr> true_branch_output_data_arrows_; 146 std::vector<DataArrowPtr> false_branch_output_data_arrows_; 147 148 kernel::LiteKernel *true_partial_node_ = nullptr; 149 kernel::LiteKernel *false_partial_node_ = nullptr; 150 kernel::LiteKernel *switch_node_ = nullptr; 151 kernel::LiteKernel *call_node_ = nullptr; 152 std::vector<lite::Tensor *> output_tensors_{}; 153 154 std::vector<OpDataPtr<Tensor>> true_branch_outputs_data_; 155 std::vector<OpDataPtr<Tensor>> false_branch_outputs_data_; 156 }; 157 #endif 158 159 int MindrtInit(); 160 void MindrtTerminate(const std::vector<std::shared_ptr<LiteOpActor>> &); 161 162 static std::atomic_int64_t actor_count = 0; 163 std::vector<std::shared_ptr<LiteOpActor>> CreateOpActor(const std::vector<kernel::LiteKernel *> &kernels, 164 const lite::InnerContext *ctx); 165 } // namespace mindspore::lite 166 #endif // MINDSPORE_LITE_SRC_LITE_MINDRT_H_ 167