LCOV - code coverage report
Current view: top level - adump/manage/dump_manager - dump_stream_info.h (source / functions) Coverage Total Hit
Test: coverage.info Lines: 100.0 % 60 60
Test Date: 2026-07-28 10:54:24 Functions: 100.0 % 11 11

            Line data    Source code
       1              : /**
       2              :  * Copyright (c) 2026 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              : #ifndef DUMP_STREAM_INFO_H
      11              : #define DUMP_STREAM_INFO_H
      12              : 
      13              : #include <map>
      14              : #include <mutex>
      15              : #include <string>
      16              : #include <iostream>
      17              : #include <memory>
      18              : #include <condition_variable>
      19              : #include <chrono>
      20              : #include <thread>
      21              : #include <queue>
      22              : #include <atomic>
      23              : #include <sstream>
      24              : #include <cstdint>
      25              : #include <algorithm>
      26              : #include <cstring>
      27              : #include <vector>
      28              : #include "acl/acl_base.h"
      29              : #include "acl/acl_rt.h"
      30              : #include "log/adx_log.h"
      31              : #include "adump_pub.h"
      32              : #include "dump_tensor.h"
      33              : #include "proto/dump_task.pb.h"
      34              : #include "dump_memory.h"
      35              : #include "runtime/runtime/context.h"
      36              : #include "runtime/runtime/event.h"
      37              : #include "runtime/runtime/stream.h"
      38              : #include "runtime/rts/rts_stream.h"
      39              : #include "runtime/rts/rts_kernel.h"
      40              : 
      41              : namespace Adx {
      42              : constexpr uint32_t DUMP_SLICE_SIZE = 128 * 1024 * 1024; // 128MB
      43              : 
      44              : struct ChunkContext {
      45              :     std::vector<char>& buffer;
      46              :     size_t& offset;
      47              :     const std::string& fileName;
      48              : };
      49              : typedef struct DumpStreamInfo {
      50              :     rtStream_t stm;
      51              :     rtEvent_t mainStmEvt;
      52              :     rtEvent_t dumpStmEvt;
      53              :     rtContext_t ctx{nullptr};
      54              :     std::vector<DumpTensor> inputTensors;
      55              :     std::vector<DumpTensor> outputTensors;
      56              :     std::string mainStreamKey;
      57              :     std::string opType;
      58              :     std::string opName;
      59              :     uint32_t dumpStmId;
      60              :     uint32_t dumpEvtId;
      61              :     uint32_t mainEvtId;
      62              :     uint32_t taskId;
      63              :     uint32_t streamId;
      64              :     uint32_t deviceId;
      65              :     uint32_t contextId;
      66              :     uint32_t threadId;
      67              :     uint64_t timestamp;
      68              :     uint64_t dumpNumber;
      69              :     std::string dumpPath;
      70              : } DumpStreamInfo;
      71              : 
      72              : typedef struct DumpInfoParams {
      73              :     std::string mainStreamKey;
      74              :     std::vector<DumpTensor> inputTensors;
      75              :     std::vector<DumpTensor> outputTensors;
      76              :     std::string opType;
      77              :     std::string opName;
      78              :     uint32_t streamId;
      79              :     uint32_t taskId;
      80              :     uint32_t deviceId;
      81              :     uint32_t contextId;
      82              :     uint32_t threadId;
      83              :     std::string dumpPath;
      84              : } DumpInfoParams;
      85              : 
      86              : int32_t DumpStreamCreate(DumpStreamInfo** ptr);
      87              : void DumpStreamFree(DumpStreamInfo* ptr);
      88              : uint64_t GetNextDumpNumber();
      89              : 
      90              : std::string GenerateDumpFileName(const DumpStreamInfo* dumpInfoPtr);
      91              : void FillTensorProtoInfo(const std::vector<DumpTensor>& tensors, toolkit::dump::DumpData& data, bool isInput);
      92              : toolkit::dump::DumpData BuildDumpDataProto(const DumpStreamInfo* dumpInfoPtr);
      93              : size_t CalculateTensorDataSize(const std::vector<DumpTensor>& tensors);
      94              : 
      95              : int32_t DumpTensorPushToDumpQueue(
      96              :     void* dataBuf, uint32_t bufLen, const char* fileName, uint64_t offset, uint32_t isLastChunk);
      97              : int32_t FlushCurrentChunk(ChunkContext& ctx, uint32_t isLastChunk);
      98              : int32_t CopyTensorDataWithFlush(const DumpTensor& tensor, ChunkContext& ctx, bool isLastTensorForChunk);
      99              : int32_t CopyTensorsWithChunking(const std::vector<DumpTensor>& tensors, ChunkContext& ctx, bool isLastTensorList);
     100              : void DumpTensorToQueue(DumpStreamInfo* dumpInfoPtr);
     101              : 
     102              : int32_t CollectStreamContextInfo(
     103              :     aclrtStream mainStream, const std::string& opName, const std::string& opType, uint32_t& streamId, uint32_t& taskId,
     104              :     uint32_t& deviceId, std::string& dumpPath);
     105              : void DumpDataRecordInCaptureStream(void* fnArgs);
     106              : int32_t SetupAsyncDump(
     107              :     std::shared_ptr<DumpStreamInfo> dumpInfoPtr, const std::string& opName, const std::string& opType,
     108              :     aclrtStream mainStream);
     109              : int32_t GetDumpInfoFromMap(DumpInfoParams& params);
     110              : 
     111           38 : inline int32_t GetPrimaryFormat(int32_t format)
     112              : {
     113           38 :     return static_cast<int32_t>(static_cast<uint32_t>(format) & 0xffU);
     114              : }
     115              : 
     116           44 : inline int32_t GetSubFormat(int32_t format)
     117              : {
     118           44 :     return static_cast<int32_t>((static_cast<uint32_t>(format) & 0xffff00U) >> 8);
     119              : }
     120              : 
     121              : class DumpResourceSafeMap {
     122              : public:
     123          897 :     static DumpResourceSafeMap& Instance()
     124              :     {
     125          907 :         static DumpResourceSafeMap instance;
     126          897 :         return instance;
     127              :     }
     128              : 
     129              :     static void WaitInterval(uint32_t intervalSec);
     130              : 
     131           93 :     void insert(const std::string key, std::shared_ptr<DumpStreamInfo> ptr)
     132              :     {
     133           93 :         std::lock_guard<std::mutex> lock(mtx_);
     134           93 :         resourceMap_[key] = std::move(ptr);
     135           93 :     }
     136              : 
     137           48 :     void remove(const std::string key)
     138              :     {
     139           48 :         std::lock_guard<std::mutex> lock(mtx_);
     140           48 :         resourceMap_.erase(key);
     141           48 :     }
     142              : 
     143           60 :     std::shared_ptr<DumpStreamInfo> get(const std::string key)
     144              :     {
     145           60 :         std::lock_guard<std::mutex> lock(mtx_);
     146           60 :         auto it = resourceMap_.find(key);
     147           60 :         if (it != resourceMap_.end()) {
     148           24 :             return it->second;
     149              :         }
     150           36 :         return nullptr;
     151           60 :     }
     152              : 
     153           51 :     int32_t size()
     154              :     {
     155           51 :         std::lock_guard<std::mutex> lock(mtx_);
     156          102 :         return resourceMap_.size();
     157           51 :     }
     158              : 
     159          408 :     void clear()
     160              :     {
     161          408 :         std::lock_guard<std::mutex> lock(mtx_);
     162          408 :         resourceMap_.clear();
     163          408 :     }
     164              : 
     165          216 :     void waitAndClear()
     166              :     {
     167              :         // 等待 resourceMap_ 中的数据被清理
     168              :         // 检查是否有待处理的 dump 任务,如果有则等待 5 秒让任务完成
     169          216 :         constexpr uint32_t WAIT_INTERVAL_SEC = 5U;
     170          216 :         constexpr uint32_t MAX_WAIT_COUNT = 12U; // 最多等待 60 秒 (5s * 12)
     171          216 :         uint32_t waitCount = 0U;
     172              : 
     173          372 :         while (waitCount < MAX_WAIT_COUNT) {
     174              :             {
     175          360 :                 std::lock_guard<std::mutex> lock(mtx_);
     176          360 :                 if (resourceMap_.empty()) {
     177          204 :                     IDE_LOGI("resourceMap_ is empty, proceed to cleanup");
     178          204 :                     break;
     179              :                 }
     180          156 :                 IDE_LOGI(
     181              :                     "resourceMap_ has %zu items, wait %us for dump tasks to complete, count: %u/%u",
     182              :                     resourceMap_.size(), WAIT_INTERVAL_SEC, waitCount + 1, MAX_WAIT_COUNT);
     183          360 :             }
     184              : 
     185              :             // map 不为空,等待 5 秒让任务完成
     186          156 :             WaitInterval(WAIT_INTERVAL_SEC);
     187          156 :             waitCount++;
     188              :         }
     189              : 
     190          216 :         if (waitCount >= MAX_WAIT_COUNT) {
     191           12 :             std::lock_guard<std::mutex> lock(mtx_);
     192           12 :             IDE_LOGW("Wait timeout, resourceMap_ still has %zu items", resourceMap_.size());
     193           12 :         }
     194              : 
     195              :         // 停止 cleanup 线程并清理资源
     196          216 :         StopCleanupThread();
     197              :         {
     198          216 :             std::lock_guard<std::mutex> lock(mtx_);
     199          216 :             resourceMap_.clear();
     200          216 :         }
     201          216 :         IDE_LOGI("All dump operations completed and resources cleared");
     202          216 :     }
     203              : 
     204              :     void EnqueueCleanup(const std::string key);
     205              :     bool IsCleanupThreadActive();
     206              : 
     207              : private:
     208              :     void StartCleanupThread();
     209              :     void StopCleanupThread();
     210              :     void CleanupThreadLoop();
     211              : 
     212            3 :     DumpResourceSafeMap() : cleanupThreadActive_(false)
     213            3 :     {}
     214            3 :     ~DumpResourceSafeMap()
     215              :     {
     216            3 :         StopCleanupThread();
     217            3 :         std::lock_guard<std::mutex> lock(mtx_);
     218            3 :         resourceMap_.clear();
     219            3 :     }
     220              :     DumpResourceSafeMap(const DumpResourceSafeMap&) = delete;
     221              :     DumpResourceSafeMap& operator=(const DumpResourceSafeMap&) = delete;
     222              : 
     223              :     std::map<const std::string, std::shared_ptr<DumpStreamInfo>> resourceMap_;
     224              :     std::mutex mtx_;
     225              : 
     226              :     std::thread cleanupThread_;
     227              :     std::queue<std::string> cleanupQueue_;
     228              :     std::mutex cleanupMtx_;
     229              :     std::condition_variable cleanupCv_;
     230              :     std::atomic<bool> cleanupThreadActive_;
     231              : };
     232              : } // namespace Adx
     233              : #endif
        

Generated by: LCOV version 2.0-1