You can not select more than 25 topics Topics must start with a chinese character,a letter or number, can include dashes ('-') and can be up to 35 characters long.

single_op_unittest.cc 6.7 kB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189
  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. #include <gtest/gtest.h>
  17. #include <vector>
  18. #include "runtime/rt.h"
  19. #define protected public
  20. #define private public
  21. #include "single_op/single_op.h"
  22. #include "single_op/single_op_manager.h"
  23. #undef private
  24. #undef protected
  25. using namespace std;
  26. using namespace ge;
  27. class UtestSingleOp : public testing::Test {
  28. protected:
  29. void SetUp() {}
  30. void TearDown() {}
  31. };
  32. TEST_F(UtestSingleOp, test_dynamic_singleop_execute_async) {
  33. uintptr_t resource_id = 0;
  34. std::mutex stream_mu;
  35. rtStream_t stream = nullptr;
  36. rtStreamCreate(&stream, 0);
  37. DynamicSingleOp dynamic_single_op(resource_id, &stream_mu, stream);
  38. vector<int64_t> dims_vec_0 = {2};
  39. vector<GeTensorDesc> input_desc;
  40. GeTensorDesc tensor_desc_0(GeShape(dims_vec_0), FORMAT_NCHW, DT_INT32);
  41. // input data from device
  42. AttrUtils::SetInt(tensor_desc_0, ATTR_NAME_PLACEMENT, 0);
  43. input_desc.emplace_back(tensor_desc_0);
  44. vector<DataBuffer> input_buffers;
  45. ge::DataBuffer data_buffer;
  46. data_buffer.data = new char[4];
  47. data_buffer.length = 4;
  48. input_buffers.emplace_back(data_buffer);
  49. vector<GeTensorDesc> output_desc;
  50. vector<DataBuffer> output_buffers;
  51. // UpdateRunInfo failed
  52. EXPECT_EQ(dynamic_single_op.ExecuteAsync(input_desc, input_buffers, output_desc, output_buffers), ACL_ERROR_GE_PARAM_INVALID);
  53. }
  54. TEST_F(UtestSingleOp, test_dynamic_singleop_execute_async1) {
  55. uintptr_t resource_id = 0;
  56. std::mutex stream_mu;
  57. rtStream_t stream = nullptr;
  58. rtStreamCreate(&stream, 0);
  59. DynamicSingleOp dynamic_single_op(resource_id, &stream_mu, stream);
  60. dynamic_single_op.num_inputs_ = 1;
  61. vector<int64_t> dims_vec_0 = {2};
  62. vector<GeTensorDesc> input_desc;
  63. GeTensorDesc tensor_desc_0(GeShape(dims_vec_0), FORMAT_NCHW, DT_INT32);
  64. // input data from host
  65. AttrUtils::SetInt(tensor_desc_0, ATTR_NAME_PLACEMENT, 1);
  66. input_desc.emplace_back(tensor_desc_0);
  67. int64_t input_size = 0;
  68. EXPECT_EQ(TensorUtils::GetTensorMemorySizeInBytes(tensor_desc_0, input_size), SUCCESS);
  69. EXPECT_EQ(input_size, 64);
  70. EXPECT_NE(SingleOpManager::GetInstance().GetResource(resource_id, stream), nullptr);
  71. vector<DataBuffer> input_buffers;
  72. ge::DataBuffer data_buffer;
  73. data_buffer.data = new char[4];
  74. data_buffer.length = 4;
  75. input_buffers.emplace_back(data_buffer);
  76. vector<GeTensorDesc> output_desc;
  77. vector<DataBuffer> output_buffers;
  78. auto *tbe_task = new (std::nothrow) TbeOpTask();
  79. ge::OpDescPtr op_desc = std::make_shared<OpDesc>("Mul", MATMUL);
  80. ge::ComputeGraphPtr graph = std::make_shared<ge::ComputeGraph>("default");
  81. ge::NodePtr node = graph->AddNode(op_desc);
  82. tbe_task->node_ = node;
  83. dynamic_single_op.op_task_.reset((OpTask *)(tbe_task));
  84. OpDescPtr desc_ptr = MakeShared<OpDesc>("name1", "type1");
  85. EXPECT_EQ(desc_ptr->AddInputDesc("x", GeTensorDesc(GeShape({2}), FORMAT_NCHW)), GRAPH_SUCCESS);
  86. dynamic_single_op.op_task_->op_desc_ = desc_ptr;
  87. // UpdateRunInfo failed
  88. EXPECT_EQ(dynamic_single_op.ExecuteAsync(input_desc, input_buffers, output_desc, output_buffers), PARAM_INVALID);
  89. }
  90. TEST_F(UtestSingleOp, test_singleop_execute_async1) {
  91. StreamResource *res = new (std::nothrow) StreamResource(1);
  92. std::mutex stream_mu;
  93. rtStream_t stream = nullptr;
  94. rtStreamCreate(&stream, 0);
  95. SingleOp single_op(res, &stream_mu, stream);
  96. vector<DataBuffer> input_buffers;
  97. ge::DataBuffer data_buffer;
  98. data_buffer.data = new char[4];
  99. data_buffer.length = 4;
  100. data_buffer.placement = 1;
  101. input_buffers.emplace_back(data_buffer);
  102. vector<DataBuffer> output_buffers;
  103. single_op.input_sizes_.emplace_back(4);
  104. SingleOpModelParam model_params;
  105. single_op.running_param_.reset(new (std::nothrow)SingleOpModelParam(model_params));
  106. single_op.args_.resize(1);
  107. EXPECT_EQ(single_op.hybrid_model_executor_, nullptr);
  108. EXPECT_EQ(single_op.running_param_->mem_base, nullptr);
  109. EXPECT_EQ(single_op.tasks_.size(), 0);
  110. EXPECT_EQ(single_op.ExecuteAsync(input_buffers, output_buffers), SUCCESS);
  111. }
  112. TEST_F(UtestSingleOp, test_singleop_execute_async2) {
  113. StreamResource *res = new (std::nothrow) StreamResource(1);
  114. std::mutex stream_mu;
  115. rtStream_t stream = nullptr;
  116. rtStreamCreate(&stream, 0);
  117. SingleOp single_op(res, &stream_mu, stream);
  118. vector<DataBuffer> input_buffers;
  119. ge::DataBuffer data_buffer;
  120. data_buffer.data = new char[4];
  121. data_buffer.length = 4;
  122. data_buffer.placement = 1;
  123. input_buffers.emplace_back(data_buffer);
  124. vector<DataBuffer> output_buffers;
  125. single_op.input_sizes_.emplace_back(4);
  126. SingleOpModelParam model_params;
  127. single_op.running_param_.reset(new (std::nothrow)SingleOpModelParam(model_params));
  128. single_op.args_.resize(1);
  129. GeTensorDesc tensor_desc(GeShape({1}), FORMAT_NHWC, DT_UINT64);
  130. single_op.inputs_desc_.emplace_back(tensor_desc);
  131. std::shared_ptr<ge::GeRootModel> root_model = ge::MakeShared<ge::GeRootModel>();
  132. single_op.hybrid_model_.reset(new (std::nothrow)hybrid::HybridModel(root_model));
  133. single_op.hybrid_model_executor_.reset(new (std::nothrow)hybrid::HybridModelExecutor(single_op.hybrid_model_.get(), 0, stream));
  134. EXPECT_EQ(single_op.running_param_->mem_base, nullptr);
  135. EXPECT_EQ(single_op.tasks_.size(), 0);
  136. GeTensorDesc tensor;
  137. int64_t storage_format_val = static_cast<Format>(FORMAT_NCHW);
  138. AttrUtils::SetInt(tensor, "storage_format", storage_format_val);
  139. std::vector<int64_t> storage_shape{1, 1, 1, 1};
  140. AttrUtils::SetListInt(tensor, "storage_shape", storage_shape);
  141. single_op.inputs_desc_.emplace_back(tensor);
  142. EXPECT_EQ(single_op.ExecuteAsync(input_buffers, output_buffers), PARAM_INVALID);
  143. }
  144. TEST_F(UtestSingleOp, test_set_host_mem) {
  145. std::mutex stream_mu_;
  146. DynamicSingleOp single_op(0, &stream_mu_, nullptr);
  147. vector<DataBuffer> input_buffers;
  148. DataBuffer data_buffer;
  149. input_buffers.emplace_back(data_buffer);
  150. vector<GeTensorDesc> input_descs;
  151. GeTensorDesc tensor_desc1;
  152. input_descs.emplace_back(tensor_desc1);
  153. vector<GeTensorDescPtr> op_input_descs;
  154. auto tensor_desc2 = std::make_shared<GeTensorDesc>();
  155. op_input_descs.emplace_back(tensor_desc2);
  156. single_op.tensor_with_hostmem_[0] = op_input_descs;
  157. EXPECT_EQ(single_op.SetHostTensorValue(input_descs, input_buffers), SUCCESS);
  158. }

图引擎模块(GE)是MindSpore的一个子模块,其代码由C++实现,位于前端模块ME和底层硬件之间,起到承接作用。图引擎模块以ME下发的图作为输入,然后进行一系列的深度图优化操作,最后输出一张可以在底层硬件上高效运行的图。GE针对昇腾AI处理器的硬件结构特点,做了特定的优化工作,以此来充分发挥出昇腾AI处理器的强大算力。在进行模型训练/推理时,GE会被自动调用而用户并不感知。GE主要由GE API和GE Core两部分组成,详细的架构图如下所示