Line data Source code
1 : /**
2 : * Copyright (c) 2025 Huawei Technologies Co., Ltd.
3 : * This program is free software, you can redistribute it and/or modify it under the terms and conditions of
4 : * CANN Open Software License Agreement Version 2.0 (the "License").
5 : * Please refer to the License for details. You may not use this file except in compliance with the License.
6 : * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED,
7 : * INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY, OR FITNESS FOR A PARTICULAR PURPOSE.
8 : * See LICENSE in the root of the software repository for the full text of the License.
9 : */
10 : #include "operator_dumper.h"
11 : #include "runtime/rt.h"
12 : #include "rts/rts_device.h"
13 : #include "rts/rts_stream.h"
14 : #include "rts/rts_kernel.h"
15 : #include "aicpu_sched/common/aicpu_task_struct.h"
16 : #include "dump_datatype.h"
17 : #include "dump_memory.h"
18 : #include "log/adx_log.h"
19 :
20 : namespace Adx {
21 : namespace {
22 : constexpr uint32_t AI_CPU_LOAD_FLAG = 1U;
23 : constexpr uint32_t TASK_ID_BITS_MASK = 0x0000FFFFU; // 16 bits, 1111,1111,1111,1111
24 : constexpr int32_t TASK_ID_LEN_16 = 16;
25 : constexpr char DUMP_KERNAL_OP_NAME[] = "DumpDataInfo";
26 : // Dump开关的device内存
27 : void *g_devMemDumpSwitch{nullptr};
28 : // 静态图下发Dump算子proto的device内存
29 : std::vector<void *> g_devMemProtoInfo;
30 : constexpr uint32_t DUMP_SWITCH_DUMP_TENSOR = 0x1U;
31 : constexpr uint32_t DUMP_SWITCH_DUMP_STATS = 0x2U;
32 : constexpr uint32_t DUMP_SWITCH_DUMP_OVERFLOW = 0x4U;
33 : } // namespace
34 :
35 54 : OperatorDumper::OperatorDumper(const std::string &opType, const std::string &opName)
36 54 : : opType_(opType), opName_(opName), stream_(nullptr)
37 : {
38 54 : }
39 :
40 318 : OperatorDumper::OperatorDumper(const DumpSetting &setting)
41 318 : : setting_(setting)
42 : {
43 318 : }
44 :
45 54 : OperatorDumper &OperatorDumper::SetDumpSetting(const DumpSetting &setting)
46 : {
47 54 : setting_ = setting;
48 54 : return *this;
49 : }
50 :
51 54 : OperatorDumper &OperatorDumper::InputDumpTensor(const std::vector<DumpTensor> &inputTensors)
52 : {
53 54 : inputTensors_ = inputTensors;
54 54 : return *this;
55 : }
56 54 : OperatorDumper &OperatorDumper::OutputDumpTensor(const std::vector<DumpTensor> &outputTensors)
57 : {
58 54 : outputTensors_ = outputTensors;
59 54 : return *this;
60 : }
61 :
62 18 : int32_t OperatorDumper::InitDevMemDumpSwitch()
63 : {
64 18 : if (g_devMemDumpSwitch == nullptr) {
65 18 : uint64_t dumpSwitchSize = static_cast<uint64_t>(sizeof(uint64_t));
66 18 : uint16_t moduleId = static_cast<uint16_t>(IDEDD);
67 18 : rtError_t rtRet = rtMalloc(&g_devMemDumpSwitch, dumpSwitchSize, RT_MEMORY_HBM, moduleId);
68 18 : IDE_CTRL_VALUE_FAILED(rtRet == RT_ERROR_NONE, return ADUMP_FAILED,
69 : "rtMalloc for dump switch on device failed! ret: 0x%X", rtRet);
70 15 : IDE_LOGI("rtMalloc for dump switch on device success. addr: %p, size: %lu",
71 : g_devMemDumpSwitch, dumpSwitchSize);
72 :
73 15 : if (SetDevMemDumpSwitch() != ADUMP_SUCCESS) {
74 3 : IDE_LOGE("Init to set dump switch on device failed!");
75 3 : DumpMemory::FreeDevice(g_devMemDumpSwitch);
76 3 : return ADUMP_FAILED;
77 : }
78 : }
79 12 : return ADUMP_SUCCESS;
80 : }
81 :
82 333 : int32_t OperatorDumper::SetDevMemDumpSwitch()
83 : {
84 333 : if (g_devMemDumpSwitch != nullptr) {
85 15 : uint64_t dumpSwitch = GetDevMemDumpSwitch();
86 15 : uint64_t dumpSwitchSize = static_cast<uint64_t>(sizeof(uint64_t));
87 15 : rtError_t rtRet = rtMemcpy(
88 : g_devMemDumpSwitch, dumpSwitchSize, &dumpSwitch, dumpSwitchSize, RT_MEMCPY_HOST_TO_DEVICE);
89 15 : IDE_CTRL_VALUE_FAILED(rtRet == RT_ERROR_NONE, return ADUMP_FAILED,
90 : "rtMemcpy for dump switch on device failed! ret: 0x%X", rtRet);
91 12 : IDE_LOGI("Set dump switch on device success. addr: %p, dump switch: %lu", g_devMemDumpSwitch, dumpSwitch);
92 : }
93 330 : return ADUMP_SUCCESS;
94 : }
95 :
96 15 : uint64_t OperatorDumper::GetDevMemDumpSwitch()
97 : {
98 15 : uint64_t dumpSwitch = 0;
99 15 : if (setting_.GetDumpStatusEx()) {
100 12 : dumpSwitch |= (setting_.IsDumpDataStats()) ? DUMP_SWITCH_DUMP_STATS : DUMP_SWITCH_DUMP_TENSOR;
101 : }
102 15 : if (setting_.GetDumpDebugStatus()) {
103 3 : dumpSwitch |= DUMP_SWITCH_DUMP_OVERFLOW;
104 3 : if (!setting_.GetDumpStatusEx()) {
105 : // 默认tensor的溢出检测
106 3 : dumpSwitch |= DUMP_SWITCH_DUMP_TENSOR;
107 : }
108 : }
109 15 : return dumpSwitch;
110 : }
111 :
112 366 : void OperatorDumper::FreeDevMemProtoCache()
113 : {
114 384 : for (void* devMemPtr : g_devMemProtoInfo) {
115 18 : DumpMemory::FreeDevice(devMemPtr);
116 : }
117 366 : g_devMemProtoInfo.clear();
118 366 : IDE_LOGI("Free all proto messages on device success.");
119 366 : }
120 :
121 318 : int32_t OperatorDumper::UpdateDevMemCache()
122 : {
123 318 : FreeDevMemProtoCache();
124 318 : return SetDevMemDumpSwitch();
125 : }
126 :
127 48 : void OperatorDumper::FreeDevMemCache()
128 : {
129 48 : if (g_devMemDumpSwitch != nullptr) {
130 12 : DumpMemory::FreeDevice(g_devMemDumpSwitch);
131 12 : IDE_LOGI("Free the dump switch on device success.");
132 : }
133 48 : FreeDevMemProtoCache();
134 48 : }
135 :
136 54 : OperatorDumper &OperatorDumper::RuntimeStream(aclrtStream stream)
137 : {
138 54 : stream_ = stream;
139 54 : return *this;
140 : }
141 :
142 30 : int32_t OperatorDumper::Launch()
143 : {
144 30 : IDE_LOGI("Start to launch dump with cfg for op %s[%s], inputSize(%zu), outputSize(%zu).",
145 : opName_.c_str(), opType_.c_str(), inputTensors_.size(), outputTensors_.size());
146 :
147 30 : IDE_CTRL_VALUE_FAILED(FillOpMappingInfo() == ADUMP_SUCCESS, return ADUMP_FAILED,
148 : "Fill op mapping info failed!");
149 :
150 18 : IDE_CTRL_VALUE_FAILED(LaunchDumpKernel() == ADUMP_SUCCESS,
151 : return ADUMP_FAILED, "Launch dump kernal failed!");
152 9 : return ADUMP_SUCCESS;
153 : }
154 :
155 18 : int32_t OperatorDumper::LaunchWithCfg(const DumpCfg &dumpCfg)
156 : {
157 18 : IDE_LOGI("Start to launch dump with cfg for op %s[%s], inputSize(%zu), outputSize(%zu).",
158 : opName_.c_str(), opType_.c_str(), inputTensors_.size(), outputTensors_.size());
159 :
160 18 : IDE_CTRL_VALUE_FAILED(InitDevMemDumpSwitch() == ADUMP_SUCCESS, return ADUMP_FAILED,
161 : "Init dump switch on device failed!");
162 :
163 12 : IDE_CTRL_VALUE_FAILED(FillOpMappingInfo() == ADUMP_SUCCESS, return ADUMP_FAILED,
164 : "Fill op mapping info failed!");
165 :
166 : // 默认按静态图处理,下发算子后不执行同步流操作
167 12 : bool synchronize = false;
168 12 : FillOpMappingInfoWithCfg(dumpCfg, synchronize);
169 :
170 12 : IDE_CTRL_VALUE_FAILED(LaunchDumpKernel(synchronize) == ADUMP_SUCCESS, return ADUMP_FAILED,
171 : "Launch dump kernal with cfg failed!");
172 12 : return ADUMP_SUCCESS;
173 : }
174 :
175 12 : void OperatorDumper::FillOpMappingInfoWithCfg(const DumpCfg &dumpCfg, bool &synchronize)
176 : {
177 42 : for (size_t i = 0; i < dumpCfg.numAttrs; ++i) {
178 30 : DumpAttr* attr = &(dumpCfg.attrs[i]);
179 30 : switch (attr->id) {
180 3 : case DUMP_ATTR_MODEL_NAME:
181 3 : if (attr->value.modelName != nullptr) {
182 9 : opMappingInfo_.set_model_name(std::string(attr->value.modelName));
183 3 : IDE_LOGD("Fill opMapping model_name: %s", attr->value.modelName);
184 : }
185 3 : break;
186 3 : case DUMP_ATTR_MODEL_ID:
187 3 : opMappingInfo_.set_model_id(attr->value.modelId);
188 3 : IDE_LOGD("Fill opMapping model_id: %u", attr->value.modelId);
189 3 : break;
190 3 : case DUMP_ATTR_STEP_ID_ADDR:
191 3 : if (attr->value.stepIdAddr != 0U) {
192 3 : opMappingInfo_.set_step_id_addr(attr->value.stepIdAddr);
193 3 : IDE_LOGD("Fill opMapping step_id_add: 0x%llx", attr->value.stepIdAddr);
194 : }
195 3 : break;
196 3 : case DUMP_ATTR_ITER_PER_LOOP_ADDR:
197 3 : if (attr->value.iterPerLoopAddr != 0U) {
198 3 : opMappingInfo_.set_iterations_per_loop_addr(attr->value.iterPerLoopAddr);
199 3 : IDE_LOGD("Fill opMapping iterations_per_loop_addr: 0x%llx", attr->value.iterPerLoopAddr);
200 : }
201 3 : break;
202 3 : case DUMP_ATTR_LOOP_COND_ADDR:
203 3 : if (attr->value.loopCondAddr != 0U) {
204 3 : opMappingInfo_.set_loop_cond_addr(attr->value.loopCondAddr);
205 3 : IDE_LOGD("Fill opMapping loop_cond_addr: 0x%llx", attr->value.loopCondAddr);
206 : }
207 3 : break;
208 3 : case DUMP_ATTR_DUMP_STEP:
209 3 : if (attr->value.dumpStep != nullptr) {
210 9 : opMappingInfo_.set_dump_step(std::string(attr->value.dumpStep));
211 3 : IDE_LOGD("Fill opMapping dump_step: %s", attr->value.dumpStep);
212 : }
213 3 : break;
214 6 : case DUMP_ATTR_STREAM_MODEL:
215 : // 0:静态图,不执行同步流
216 6 : synchronize = attr->value.streamModel == 0U ? false : true;
217 6 : IDE_LOGD("to synchronize stream: %d", synchronize);
218 6 : break;
219 6 : default:
220 6 : IDE_LOGD("not support attr id: %d", attr->id);
221 6 : break;
222 : }
223 : }
224 12 : IDE_LOGD("dump_switch_addr: 0x%llx", static_cast<uint64_t>(reinterpret_cast<uintptr_t>(g_devMemDumpSwitch)));
225 12 : opMappingInfo_.set_dump_switch_addr(static_cast<uint64_t>(reinterpret_cast<uintptr_t>(g_devMemDumpSwitch)));
226 12 : }
227 :
228 42 : int32_t OperatorDumper::FillOpMappingInfo()
229 : {
230 : // Set default
231 42 : opMappingInfo_.clear_task();
232 42 : opMappingInfo_.set_flag(AI_CPU_LOAD_FLAG);
233 42 : if (setting_.IsDumpDataStats()) {
234 9 : opMappingInfo_.set_dump_data(toolkitV2::aicpu::dump::DumpData::STATS_DUMP_DATA);
235 : } else {
236 33 : opMappingInfo_.set_dump_data(toolkitV2::aicpu::dump::DumpData::TENSOR_DUMP_DATA);
237 : }
238 :
239 42 : int32_t deviceId = 0;
240 42 : rtError_t rtRet = rtGetDevice(&deviceId);
241 42 : if (rtRet != RT_ERROR_NONE || deviceId < 0) {
242 3 : IDE_LOGE("rtGetDevice failed, ret 0x%X, devId: %d", rtRet, deviceId);
243 3 : return ADUMP_FAILED;
244 : }
245 :
246 39 : IDE_CTRL_VALUE_FAILED(FillDumpPath(deviceId) == ADUMP_SUCCESS, return ADUMP_FAILED, "Fill dump path failed!");
247 :
248 39 : IDE_CTRL_VALUE_FAILED(FillDumpTask(deviceId) == ADUMP_SUCCESS, return ADUMP_FAILED, "Fill dump task failed!");
249 30 : return ADUMP_SUCCESS;
250 : }
251 :
252 39 : int32_t OperatorDumper::FillDumpPath(int32_t deviceId)
253 : {
254 39 : Path dumpPathWithDevId(setting_.GetDumpPath());
255 39 : dumpPathWithDevId.Append(std::to_string(deviceId));
256 78 : opMappingInfo_.set_dump_path(dumpPathWithDevId.GetString());
257 39 : IDE_LOGI("Dump op to path %s.", dumpPathWithDevId.GetCString());
258 39 : return ADUMP_SUCCESS;
259 39 : }
260 :
261 39 : int32_t OperatorDumper::FillDumpTask(int32_t deviceId)
262 : {
263 39 : toolkitV2::aicpu::dump::Task task;
264 39 : task.mutable_op()->set_op_name(opName_);
265 39 : task.mutable_op()->set_op_type(opType_);
266 :
267 39 : uint32_t taskId = 0U;
268 39 : rtError_t rtRet = rtsGetThreadLastTaskId(&taskId);
269 39 : if (rtRet != RT_ERROR_NONE) {
270 3 : IDE_LOGE("Call rtsGetThreadLastTaskId failed, ret 0x%X", rtRet);
271 3 : return ADUMP_FAILED;
272 : }
273 :
274 36 : int32_t streamId = 0U;
275 36 : rtRet = rtsStreamGetId(stream_, &streamId);
276 36 : if (rtRet != RT_ERROR_NONE) {
277 3 : IDE_LOGE("Call rtsStreamGetId failed, ret 0x%X", rtRet);
278 3 : return ADUMP_FAILED;
279 : }
280 :
281 33 : int32_t taskIdLen = 0;
282 33 : rtRet = rtsDeviceGetCapability(deviceId, RT_FEATURE_SYSTEM_TASKID_BIT_WIDTH, &taskIdLen);
283 33 : if (rtRet != RT_ERROR_NONE) {
284 3 : IDE_LOGE("Call rtsDeviceGetCapability failed, ret 0x%X", rtRet);
285 3 : return ADUMP_FAILED;
286 : }
287 30 : if (taskIdLen == TASK_ID_LEN_16) {
288 30 : taskId = taskId & TASK_ID_BITS_MASK;
289 : }
290 :
291 30 : task.set_task_id(taskId);
292 30 : task.set_stream_id(static_cast<uint32_t>(streamId));
293 30 : IDE_LOGI("Task id is %u, stream id is %d", taskId, streamId);
294 :
295 30 : uint32_t dumpMode = setting_.GetDumpMode();
296 30 : if ((dumpMode & DUMP_MODE_OUTPUT) != 0) {
297 30 : DumpOutput(task);
298 : }
299 :
300 30 : if ((dumpMode & DUMP_MODE_INPUT) != 0) {
301 30 : DumpInput(task);
302 : }
303 :
304 30 : opMappingInfo_.mutable_task()->Add(std::move(task));
305 30 : return ADUMP_SUCCESS;
306 39 : }
307 :
308 45 : toolkitV2::aicpu::dump::AddressType OperatorDumper::ConvertAddressType(const DumpTensor &dumpTensor)
309 : {
310 45 : AddressType addressType = dumpTensor.GetAddressType();
311 45 : if (addressType == AddressType::NOTILING) {
312 3 : return toolkitV2::aicpu::dump::AddressType::NOTILING_ADDR;
313 42 : } else if (addressType == AddressType::RAW) {
314 15 : return toolkitV2::aicpu::dump::AddressType::RAW_ADDR;
315 : } else {
316 27 : return toolkitV2::aicpu::dump::AddressType::TRADITIONAL_ADDR;
317 : }
318 : }
319 :
320 30 : void OperatorDumper::DumpInput(toolkitV2::aicpu::dump::Task &task)
321 : {
322 54 : for (const auto &dumpTensor : inputTensors_) {
323 24 : toolkitV2::aicpu::dump::Input input;
324 24 : auto ir_data_type = DumpDataType::GetIrDataType(static_cast<GeDataType>(dumpTensor.GetDataType()));
325 24 : input.set_data_type(static_cast<int32_t>(ir_data_type));
326 24 : input.set_format(static_cast<int32_t>(dumpTensor.GetFormat()));
327 :
328 24 : std::vector<int64_t> shape = dumpTensor.GetShape();
329 45 : for (auto dim : shape) {
330 21 : input.mutable_shape()->add_dim(static_cast<uint64_t>(dim));
331 : }
332 24 : std::vector<int64_t> originShape = dumpTensor.GetOriginShape();
333 45 : for (auto dim : originShape) {
334 21 : input.mutable_origin_shape()->add_dim(static_cast<uint64_t>(dim));
335 : }
336 :
337 24 : size_t dumpSize = dumpTensor.GetSize();
338 24 : const void *dumpAddr = dumpTensor.GetAddress();
339 24 : input.set_size(static_cast<uint64_t>(dumpSize));
340 24 : input.set_address(static_cast<uint64_t>(reinterpret_cast<uintptr_t>(dumpAddr)));
341 24 : IDE_LOGI("Dump op(%s) input addr(%p), size(%zu).", opName_.c_str(), dumpAddr, dumpSize);
342 24 : input.set_addr_type(ConvertAddressType(dumpTensor));
343 24 : task.mutable_input()->Add(std::move(input));
344 24 : }
345 30 : }
346 :
347 30 : void OperatorDumper::DumpOutput(toolkitV2::aicpu::dump::Task &task)
348 : {
349 51 : for (const auto &dumpTensor : outputTensors_) {
350 21 : toolkitV2::aicpu::dump::Output output;
351 21 : auto ir_data_type = DumpDataType::GetIrDataType(static_cast<GeDataType>(dumpTensor.GetDataType()));
352 21 : output.set_data_type(static_cast<int32_t>(ir_data_type));
353 21 : output.set_format(static_cast<int32_t>(dumpTensor.GetFormat()));
354 21 : std::vector<int64_t> shape = dumpTensor.GetShape();
355 42 : for (auto dim : shape) {
356 21 : output.mutable_shape()->add_dim(static_cast<uint64_t>(dim));
357 : }
358 21 : std::vector<int64_t> originShape = dumpTensor.GetOriginShape();
359 42 : for (auto dim : originShape) {
360 21 : output.mutable_origin_shape()->add_dim(static_cast<uint64_t>(dim));
361 : }
362 :
363 21 : size_t dumpSize = dumpTensor.GetSize();
364 21 : const void *dumpAddr = dumpTensor.GetAddress();
365 21 : output.set_size(static_cast<uint64_t>(dumpSize));
366 21 : output.set_address(static_cast<uint64_t>(reinterpret_cast<uintptr_t>(dumpAddr)));
367 21 : IDE_LOGI("Dump op(%s) output addr(%p), size(%zu).", opName_.c_str(), dumpAddr, dumpSize);
368 21 : output.set_addr_type(ConvertAddressType(dumpTensor));
369 21 : task.mutable_output()->Add(std::move(output));
370 21 : }
371 30 : }
372 :
373 30 : int32_t OperatorDumper::LaunchDumpKernel(bool synchronize) const
374 : {
375 30 : std::string protoMsg;
376 30 : const size_t protoSize = opMappingInfo_.ByteSizeLong();
377 30 : const bool bRet = opMappingInfo_.SerializeToString(&protoMsg);
378 30 : if ((!bRet) || (protoSize == 0U)) {
379 0 : IDE_LOGE("Serialize proto msg failed, size is %zu", protoSize);
380 0 : return ADUMP_FAILED;
381 : }
382 :
383 30 : void *protoMsgDevMem = DumpMemory::CopyHostToDevice(protoMsg.c_str(), static_cast<uint64_t>(protoSize));
384 30 : IDE_CTRL_VALUE_FAILED(protoMsgDevMem != nullptr, return ADUMP_FAILED,
385 : "Copy proto msg to device failed! size: %zu", protoSize);
386 :
387 24 : void *protoMsgSizeDevMem = DumpMemory::CopyHostToDevice(&protoSize, static_cast<uint64_t>(sizeof(size_t)));
388 24 : if (protoMsgSizeDevMem == nullptr) {
389 0 : DumpMemory::FreeDevice(protoMsgDevMem);
390 0 : IDE_LOGE("Copy proto msg size to device failed! size: %zu", protoSize);
391 0 : return ADUMP_FAILED;
392 : }
393 24 : int32_t ret = LaunchDumpKernel(protoMsgDevMem, protoMsgSizeDevMem, synchronize);
394 24 : if (synchronize) {
395 15 : DumpMemory::FreeDevice(protoMsgDevMem);
396 15 : DumpMemory::FreeDevice(protoMsgSizeDevMem);
397 : } else {
398 9 : g_devMemProtoInfo.push_back(protoMsgDevMem);
399 9 : g_devMemProtoInfo.push_back(protoMsgSizeDevMem);
400 : }
401 24 : return ret;
402 30 : }
403 :
404 24 : int32_t OperatorDumper::LaunchDumpKernel(const void *const protoMsgDevMem,
405 : const void *const protoMsgSizeDevMem, bool synchronize) const
406 : {
407 24 : constexpr uint32_t ioAddrNum = 2U;
408 24 : constexpr uint32_t argSize = sizeof(aicpu::AicpuParamHead) + (ioAddrNum * sizeof(uint64_t));
409 24 : uint8_t args[argSize] = {};
410 :
411 : // fill head
412 24 : aicpu::AicpuParamHead *paramHead = reinterpret_cast<aicpu::AicpuParamHead *>(args);
413 24 : paramHead->length = argSize;
414 24 : paramHead->ioAddrNum = ioAddrNum;
415 :
416 : // fill body
417 24 : constexpr size_t protoMsgOffset = sizeof(aicpu::AicpuParamHead);
418 24 : constexpr size_t protoMsgSizeOffset = sizeof(aicpu::AicpuParamHead) + sizeof(uint64_t);
419 24 : uint64_t protoMsgDevAddr = static_cast<uint64_t>(reinterpret_cast<uintptr_t>(protoMsgDevMem));
420 24 : uint64_t protoMsgSizeDevAddr = static_cast<uint64_t>(reinterpret_cast<uintptr_t>(protoMsgSizeDevMem));
421 :
422 : // use memcpy to avoid 'uint64_t type 8 byte alignment requires'
423 24 : const auto cpyMsg = memcpy_s(&args[protoMsgOffset], sizeof(uint64_t), &protoMsgDevAddr, sizeof(uint64_t));
424 24 : if (cpyMsg != EOK) {
425 0 : IDE_LOGE("Copy addr to args failed");
426 0 : return ADUMP_FAILED;
427 : }
428 24 : const auto cpySize = memcpy_s(&args[protoMsgSizeOffset], sizeof(uint64_t), &protoMsgSizeDevAddr, sizeof(uint64_t));
429 24 : if (cpySize != EOK) {
430 0 : IDE_LOGE("Copy addr to args failed");
431 0 : return ADUMP_FAILED;
432 : }
433 :
434 24 : rtArgsEx_t argsInfo = {};
435 24 : argsInfo.args = reinterpret_cast<void *>(args);
436 24 : argsInfo.argsSize = argSize;
437 : // launch dump op
438 24 : rtError_t rtRet = rtCpuKernelLaunchWithFlag(nullptr, DUMP_KERNAL_OP_NAME, 1U, &argsInfo, nullptr, stream_, 0U);
439 24 : if (rtRet != RT_ERROR_NONE) {
440 3 : IDE_LOGE("rtCpuKernelLaunchWithFlag failed, ret: 0x%X", rtRet);
441 3 : return ADUMP_FAILED;
442 : }
443 :
444 21 : if (synchronize) {
445 12 : rtRet = rtStreamSynchronize(stream_);
446 12 : IDE_CTRL_VALUE_FAILED(rtRet == RT_ERROR_NONE, return ADUMP_FAILED,
447 : "rtStreamSynchronize failed, ret: 0x%X", rtRet);
448 : }
449 :
450 21 : IDE_LOGI("Kernel launch dump op %s success", opName_.c_str());
451 21 : return ADUMP_SUCCESS;
452 : }
453 : } // namespace Adx
|