LCOV - code coverage report
Current view: top level - legacy/ascend950/service/collective/alg/coll_alg_factory/alg_template/prim_alg_template - temp_reduce_scatter_mesh.cc (source / functions) Coverage Total Hit
Test: coverage.info Lines: 0.0 % 173 0
Test Date: 2026-08-04 10:52:23 Functions: 0.0 % 16 0

            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              : 
      11              : #include <numeric>
      12              : 
      13              : #include "log.h"
      14              : 
      15              : #include "temp_reduce_scatter_mesh.h"
      16              : 
      17              : namespace Hccl {
      18            0 : TempReduceScatterMesh::TempReduceScatterMesh(const RankId virtualRank, const u32 tempRankSize,
      19              :                                              const std::vector<std::vector<RankId>> &tempVTopo,
      20            0 :                                              const std::map<RankId, u32>            &tempVirtRankMap)
      21            0 :     : AlgTemplateBase(virtualRank, tempRankSize, tempVTopo, tempVirtRankMap)
      22              : {
      23            0 : }
      24              : 
      25            0 : TempReduceScatterMesh::~TempReduceScatterMesh()
      26              : {
      27            0 : }
      28              : 
      29            0 : HcclResult TempReduceScatterMesh::CalcRes(const bool forAllReduce, AlgTempResReq &tempResReq,
      30              :                                           u32 &requiredScratchMultiplier)
      31              : {
      32              :     (void)forAllReduce;
      33            0 :     tempResReq.queNum         = tempVTopo_[0].size() - 1;
      34            0 :     requiredScratchMultiplier = tempRankSize_;
      35              : 
      36            0 :     CHK_RET(CalcResLinks(tempResReq));
      37            0 :     return HcclResult::HCCL_SUCCESS;
      38              : }
      39              : 
      40            0 : HcclResult TempReduceScatterMesh::CalcResDetour(const bool forAllReduce, const RankGraph *rankGraph,
      41              :                                                 AlgTempResReq &tempResReq, u32 &requiredScratchMultiplier)
      42              : {
      43              :     (void)forAllReduce;
      44              : 
      45              :     u32 myAlgRank;
      46            0 :     CHK_RET(GetAlgRank(myRank_, tempVTopo_[0], myAlgRank));
      47              : 
      48            0 :     linkNumBtwPeers_ = GetLinkNum(rankGraph, myRank_, tempVTopo_[0][(myAlgRank + 1) % tempRankSize_]);
      49            0 :     if (linkNumBtwPeers_ == 1) {
      50            0 :         HCCL_INFO(
      51              :             "[CollAlgFactory] [TempReduceScatterMesh] [WARNING] Rank [%d], linkNum between rank [%d] and rank [%d] "
      52              :             "equals 1, not able to detour",
      53              :             myRank_, myRank_, tempVTopo_[0][(myAlgRank + 1) % tempRankSize_]);
      54            0 :         enableDetour_ = false;
      55              :     } else {
      56            0 :         enableDetour_ = true;
      57              :     }
      58              : 
      59            0 :     queNumPerNeighbor_ = (linkNumBtwPeers_ + 1) >> 1;
      60            0 :     tempResReq.queNum  = (tempVTopo_[0].size() - 1) * queNumPerNeighbor_;
      61              : 
      62            0 :     requiredScratchMultiplier = tempRankSize_;
      63              : 
      64            0 :     CHK_RET(CalcResLinks(tempResReq));
      65            0 :     return HcclResult::HCCL_SUCCESS;
      66              : }
      67              : 
      68            0 : HcclResult TempReduceScatterMesh::CalcResDetour(const bool forAllReduce, ConnectedLinkMgr *linkMgr,
      69              :                                                 AlgTempResReq &tempResReq, u32 &requiredScratchMultiplier)
      70              : {
      71              :     (void)forAllReduce;
      72              : 
      73              :     u32 myAlgRank;
      74            0 :     CHK_RET(GetAlgRank(myRank_, tempVTopo_[0], myAlgRank));
      75              : 
      76            0 :     linkNumBtwPeers_ = (linkMgr->GetLinks(tempVTopo_[0][(myAlgRank + 1) % tempRankSize_])).size();
      77              : 
      78            0 :     enableDetour_ = (linkNumBtwPeers_ == 1) ? false : true;
      79              : 
      80            0 :     queNumPerNeighbor_ = (linkNumBtwPeers_ + 1) >> 1;
      81            0 :     tempResReq.queNum  = (tempVTopo_[0].size() - 1) * queNumPerNeighbor_;
      82              : 
      83            0 :     requiredScratchMultiplier = tempRankSize_;
      84              : 
      85            0 :     CHK_RET(CalcResLinks(tempResReq));
      86            0 :     return HcclResult::HCCL_SUCCESS;
      87              : }
      88              : 
      89            0 : HcclResult TempReduceScatterMesh::CalcResLinks(AlgTempResReq &tempResReq)
      90              : {
      91              :     u32 myAlgRank;
      92            0 :     CHK_RET(GetAlgRank(myRank_, tempVTopo_[0], myAlgRank));
      93              : 
      94            0 :     for (u32 queIdx = 0; queIdx < tempVTopo_[0].size() - 1; queIdx++) {
      95              :         // find neighbors -> virtualRank
      96            0 :         RankId neighborRank = tempVTopo_[0][(myAlgRank + 1 + queIdx) % tempRankSize_];
      97              : 
      98              :         // LinkNum
      99            0 :         tempResReq.links[neighborRank] = linkNumBtwPeers_;
     100              :     }
     101              : 
     102            0 :     return HcclResult::HCCL_SUCCESS;
     103              : }
     104              : 
     105              : /*
     106              : dataSize / (rankSize) --> chunkSize
     107              : dataSize / (rankSize * queNum) --> sliceSize
     108              : 
     109              : SliceInfoVecforRing: [1st chunk: [1st Slice, 2nd Slice, ...], 2nd chunk: [1st Slice, 2nd Slice, ...], ...]
     110              : */
     111            0 : HcclResult TempReduceScatterMesh::CalcSliceInfo(const AllignInfo &allignInfo, const bool forAllReduce,
     112              :                                                 const u64 dataSize, RankSliceInfo &sliceInfoVec)
     113              : {
     114            0 :     std::vector<SliceInfo> tmp(1);
     115            0 :     sliceInfoVec.resize(tempRankSize_, tmp);
     116              : 
     117            0 :     if (forAllReduce) {
     118              :         // for allreduce, dataSize = total dataSize
     119            0 :         CHK_RET(CalcSliceInfoAllReduce(allignInfo, dataSize, sliceInfoVec));
     120              :     } else {
     121              :         // for reduce scatter, dataSize = chunkSize
     122            0 :         CHK_RET(CalcRsAgSliceInfoMesh(myRank_, tempRankSize_, allignInfo, dataSize, sliceInfoVec));
     123              :     }
     124            0 :     return HcclResult::HCCL_SUCCESS;
     125            0 : }
     126              : 
     127            0 : HcclResult TempReduceScatterMesh::CalcSliceInfoAllReduce(const AllignInfo &allignInfo, const u64 dataSize,
     128              :                                                          RankSliceInfo &sliceInfoVec) const
     129              : {
     130              :     u64 unitAllignSize;
     131            0 :     CHK_RET(GetUnitAllignSize(allignInfo, unitAllignSize));
     132              : 
     133            0 :     u64 chunkSize = RoundUp(dataSize, (tempRankSize_ * unitAllignSize)) * unitAllignSize;
     134              : 
     135            0 :     u64 accumOff = 0;
     136            0 :     for (u32 rankIdx = 0; rankIdx < tempRankSize_; rankIdx++) {
     137            0 :         u64       currChunkSize  = ((dataSize - accumOff) > chunkSize) ? chunkSize : (dataSize - accumOff);
     138            0 :         SliceInfo slice          = {accumOff, currChunkSize};
     139            0 :         sliceInfoVec[rankIdx][0] = slice;
     140            0 :         accumOff += currChunkSize;
     141              :     }
     142              : 
     143            0 :     CHK_PRT_RET((sliceInfoVec[tempRankSize_ - 1][0].offset + sliceInfoVec[tempRankSize_ - 1][0].size != dataSize),
     144              :                 HCCL_ERROR("[CollAlgFactory] [TempReduceScatterMesh] Rank [%d], SliceInfo calculation error!", myRank_),
     145              :                 HcclResult::HCCL_E_INTERNAL);
     146              : 
     147            0 :     return HcclResult::HCCL_SUCCESS;
     148              : }
     149              : 
     150            0 : HcclResult TempReduceScatterMesh::GenPrimQue(const TempFuncs &tempFuncs, const RankSliceInfo &sliceInfoVec,
     151              :                                              const BuffInfo &buffInfo, const ResLinks &tempLinks,
     152              :                                              std::vector<PrimQuePtr> &tempPrimQues)
     153              : {
     154            0 :     opMode_              = tempFuncs.opMode;
     155            0 :     enableCounterNotify_ = tempFuncs.enableCounterNotify;
     156            0 :     buffInfo_            = buffInfo;
     157              : 
     158            0 :     auto linkIter    = tempLinks.begin();
     159            0 :     linkNumBtwPeers_ = linkIter->second.size();
     160            0 :     HCCL_INFO("[CollAlgFactory] [TempReduceScatterMesh] Rank [%d], linkNumBtwPeers equals to [%u].", myRank_,
     161              :                linkNumBtwPeers_);
     162            0 :     queNumPerNeighbor_ = (linkNumBtwPeers_ + 1) >> 1;
     163            0 :     HCCL_INFO("[CollAlgFactory] [TempReduceScatterMesh] Rank [%d], queNumPerNeighbor equals to [%u].", myRank_,
     164              :                queNumPerNeighbor_);
     165            0 :     enableDetour_ = (linkNumBtwPeers_ == 1) ? false : true;
     166              : 
     167            0 :     majorQueNum_ = tempVTopo_[0].size() - 1;
     168            0 :     CHK_PRT_RET(majorQueNum_ * queNumPerNeighbor_ != tempPrimQues.size(),
     169              :                 HCCL_ERROR("[CollAlgFactory] [TempReduceScatterMesh] Rank [%d], requiredQueNum [%u] not equals to "
     170              :                            "templateQueNum [%u].",
     171              :                            myRank_, majorQueNum_ * queNumPerNeighbor_, tempPrimQues.size()),
     172              :                 HcclResult::HCCL_E_INTERNAL);
     173              : 
     174              :     // queue arrangement
     175            0 :     std::vector<PrimQuePtr> mainPrimQues;
     176            0 :     for (u32 queIdx = 0; queIdx < majorQueNum_; queIdx++) {
     177            0 :         mainPrimQues.push_back(tempPrimQues[queIdx * queNumPerNeighbor_]);
     178              :     }
     179              : 
     180              :     // LocalCopy: from input to scratch In Buffer for OPBASE
     181            0 :     if ((opMode_ == OpMode::OPBASE) && tempFuncs.isForepart) {
     182            0 :         CHK_RET(PreCopyOpbase(tempFuncs.usrData, mainPrimQues));
     183              :     }
     184              : 
     185              :     // semaphore sync
     186            0 :     if (majorQueNum_ > 1) {
     187            0 :         CHK_RET(PreSyncInterQueues(mainPrimQues));
     188              :     }
     189              : 
     190              :     // locate myRank in tempVTopo -> algRank
     191              :     u32 myAlgRank;
     192            0 :     CHK_RET(GetAlgRank(myRank_, tempVTopo_[0], myAlgRank));
     193              : 
     194              :     // run Mesh
     195            0 :     CHK_PRT_RET(
     196              :         RunMesh(myAlgRank, tempVTopo_[0], sliceInfoVec, tempLinks, tempPrimQues) != HcclResult::HCCL_SUCCESS,
     197              :         HCCL_ERROR("[CollAlgFactory] [TempReduceScatterMesh] Rank [%d], unable to run the mesh algorithm.", myRank_),
     198              :         HcclResult::HCCL_E_INTERNAL);
     199              : 
     200              :     // semaphore sync
     201            0 :     if (majorQueNum_ > 1) {
     202            0 :         CHK_RET(PostSyncInterQueues(mainPrimQues));
     203              :     }
     204              : 
     205              :     // LocalCopy for standalone reducescatter in Offload Mode
     206            0 :     if ((opMode_ == OpMode::OFFLOAD) && !tempFuncs.forAllReduce && !tempFuncs.forAlgSeqComb) {
     207            0 :         CHK_RET(PostCopyOffload(sliceInfoVec, mainPrimQues));
     208              :     }
     209              : 
     210              :     // LocalCopy from scratch to output for Opbase
     211            0 :     if (tempFuncs.isBottom && !tempFuncs.forAllReduce) {
     212            0 :         CHK_RET(PostCopyOpbase(tempFuncs.usrData, mainPrimQues));
     213              :     }
     214              : 
     215            0 :     return HcclResult::HCCL_SUCCESS;
     216            0 : }
     217              : 
     218            0 : HcclResult TempReduceScatterMesh::RunMesh(const u32 myAlgRank, const std::vector<RankId> &vTopo,
     219              :                                           const RankSliceInfo &sliceInfoVec, const ResLinks &tempLinks,
     220              :                                           std::vector<PrimQuePtr> &tempPrimQues)
     221              : {
     222            0 :     for (u32 queIdx = 0; queIdx < vTopo.size() - 1; queIdx++) {
     223              :         // find neighbors -> virtualRank
     224            0 :         RankId neighborRank = vTopo[(myAlgRank + 1 + queIdx) % tempRankSize_];
     225              : 
     226            0 :         u32 recvChunkIdx = tempVirtRankMap_[myRank_];
     227            0 :         u32 sendChunkIdx = tempVirtRankMap_[neighborRank];
     228              : 
     229              :         // queue assignment
     230            0 :         if (enableDetour_) {
     231            0 :             std::vector<PrimQuePtr> detourPrimQues;
     232            0 :             for (u32 detourIdx = 0; detourIdx < queNumPerNeighbor_; detourIdx++) {
     233            0 :                 detourPrimQues.push_back(tempPrimQues[queIdx * queNumPerNeighbor_ + detourIdx]);
     234              :             }
     235            0 :             HCCL_INFO("[CollAlgFactory] [TempReduceScatterMesh] Rank [%d], Run Mesh with Detour.", myRank_);
     236            0 :             CHK_RET(RunIndividualPeerDetour(neighborRank, sliceInfoVec[sendChunkIdx][0], sliceInfoVec[recvChunkIdx][0],
     237              :                                             tempLinks, detourPrimQues));
     238            0 :         } else {
     239            0 :             PrimQuePtr currQue          = tempPrimQues[queIdx];
     240            0 :             LinkData   neighborLinkData = tempLinks.at(neighborRank)[0];
     241            0 :             HCCL_INFO("[CollAlgFactory] [TempReduceScatterMesh] Rank [%d], Run Mesh without Detour.", myRank_);
     242            0 :             CHK_RET(RunIndividualPeer(neighborRank, neighborLinkData, sliceInfoVec[sendChunkIdx][0],
     243              :                                       sliceInfoVec[recvChunkIdx][0], currQue));
     244            0 :         }
     245              :     }
     246              : 
     247            0 :     return HcclResult::HCCL_SUCCESS;
     248              : }
     249              : 
     250            0 : HcclResult TempReduceScatterMesh::RunIndividualPeerDetour(const RankId neighborRank, const SliceInfo &sendReduceSlice,
     251              :                                                           const SliceInfo &recvReduceSlice, const ResLinks &tempLinks,
     252              :                                                           std::vector<PrimQuePtr> &detourPrimQues)
     253              : {
     254            0 :     CHK_RET(PreSyncInterQueues(detourPrimQues));
     255              : 
     256            0 :     u32 dataSizePerVolume  = DataTypeSizeGet(dataType_);
     257            0 :     u64 unitRecvReduceSize = RoundUp(recvReduceSlice.size, queNumPerNeighbor_ * dataSizePerVolume) * dataSizePerVolume;
     258            0 :     u64 resRecvReduceSize  = recvReduceSlice.size;
     259            0 :     u64 currRecvReduceOff  = recvReduceSlice.offset;
     260              : 
     261            0 :     u64 unitSendReduceSize = RoundUp(sendReduceSlice.size, queNumPerNeighbor_ * dataSizePerVolume) * dataSizePerVolume;
     262            0 :     u64 resSendReduceSize  = sendReduceSlice.size;
     263            0 :     u64 currSendReduceOff  = sendReduceSlice.offset;
     264              : 
     265            0 :     std::vector<std::vector<LinkDataIterator>> sendRecvRedLinks;
     266            0 :     CHK_RET(GetSendRecvRedLinks(neighborRank, tempLinks, sendRecvRedLinks));
     267              : 
     268            0 :     for (u32 detourIdx = 0; detourIdx < queNumPerNeighbor_; detourIdx++) {
     269            0 :         u64       currSendReduceSize  = resSendReduceSize > unitSendReduceSize ? unitSendReduceSize : resSendReduceSize;
     270            0 :         u64       currRecvReduceSize  = resRecvReduceSize > unitRecvReduceSize ? unitRecvReduceSize : resRecvReduceSize;
     271            0 :         SliceInfo currSendReduceSlice = {currSendReduceOff, currSendReduceSize};
     272            0 :         SliceInfo currRecvReduceSlice = {currRecvReduceOff, currRecvReduceSize};
     273              : 
     274              :         std::unique_ptr<PrimGroup> primGroup
     275            0 :             = RunSendRecvReduce(neighborRank, (*sendRecvRedLinks[detourIdx][0]), (*sendRecvRedLinks[detourIdx][1]),
     276            0 :                                 currSendReduceSlice, currRecvReduceSlice);
     277            0 :         detourPrimQues[detourIdx]->Append(std::move(primGroup));
     278              : 
     279            0 :         resRecvReduceSize -= currRecvReduceSize;
     280            0 :         resSendReduceSize -= currSendReduceSize;
     281            0 :         currRecvReduceOff += currRecvReduceSize;
     282            0 :         currSendReduceOff += currSendReduceSize;
     283            0 :     }
     284              : 
     285            0 :     CHK_RET(PostSyncInterQueues(detourPrimQues));
     286            0 :     return HcclResult::HCCL_SUCCESS;
     287            0 : }
     288              : 
     289            0 : HcclResult TempReduceScatterMesh::GetSendRecvRedLinks(const RankId neighborRank, const ResLinks &tempLinks,
     290              :                                                       std::vector<std::vector<LinkDataIterator>> &sendRecvLinks) const
     291              : {
     292            0 :     CHK_PRT_RET(
     293              :         ((queNumPerNeighbor_ != NUM_TWO) || (tempRankSize_ != NUM_TWO)),
     294              :         HCCL_ERROR(
     295              :             "[CollAlgFactory] [TempReduceScatterMesh] Rank [%d], detouring is supported only in 2P Mesh in 4P topo.",
     296              :             myRank_),
     297              :         HcclResult::HCCL_E_INTERNAL);
     298              : 
     299            0 :     std::vector<LinkDataIterator> tmpLinks(NUM_TWO);
     300            0 :     sendRecvLinks.resize(queNumPerNeighbor_, tmpLinks);
     301              : 
     302            0 :     CHK_PRT_RET(
     303              :         GetDetourSendRecvLinksIn4P(myRank_, neighborRank, tempLinks, sendRecvLinks),
     304              :         HCCL_ERROR("[InsCollAlgFactory] [TempReduceScatterMesh] Rank [%d], get send recv links in 2P Mesh in 4P topo.",
     305              :                    myRank_),
     306              :         HcclResult::HCCL_E_INTERNAL);
     307              : 
     308            0 :     return HcclResult::HCCL_SUCCESS;
     309            0 : }
     310              : 
     311            0 : HcclResult TempReduceScatterMesh::RunIndividualPeer(const RankId neighborRank, const LinkData &neighborLinkData,
     312              :                                                     const SliceInfo &sendReduceSlice, const SliceInfo &recvReduceSlice,
     313              :                                                     PrimQuePtr currQue) const
     314              : {
     315              :     std::unique_ptr<PrimGroup> primGroup
     316            0 :         = RunSendRecvReduce(neighborRank, neighborLinkData, neighborLinkData, sendReduceSlice, recvReduceSlice);
     317            0 :     currQue->Append(std::move(primGroup));
     318            0 :     return HcclResult::HCCL_SUCCESS;
     319            0 : }
     320              : 
     321            0 : std::unique_ptr<PrimGroup> TempReduceScatterMesh::RunSendRecvReduce(const RankId     neighborRank,
     322              :                                                                     const LinkData  &sendLinkData,
     323              :                                                                     const LinkData  &recvLinkData,
     324              :                                                                     const SliceInfo &currSendReduceSlice,
     325              :                                                                     const SliceInfo &currRecvReduceSlice) const
     326              : {
     327              :     // PrimGroup
     328            0 :     std::unique_ptr<PrimGroup> primGroup = std::make_unique<PrimGroup>();
     329              : 
     330              :     // RecvReduce
     331            0 :     u64       recvOffset      = currRecvReduceSlice.offset;
     332            0 :     u64       recvSize        = currRecvReduceSlice.size;
     333            0 :     DataSlice recvRemSlice    = DataSlice(buffInfo_.inBuffType, recvOffset + buffInfo_.inBuffBaseOff, recvSize);
     334            0 :     DataSlice recvLocSrcSlice = DataSlice(buffInfo_.scratBuffType, recvOffset + buffInfo_.scratchBuffBaseOff, recvSize);
     335            0 :     DataSlice recvLocDstSlice = DataSlice(buffInfo_.inBuffType, recvOffset + buffInfo_.inBuffBaseOff, recvSize);
     336            0 :     std::unique_ptr<Primitive> primRecvReduce = std::make_unique<PrimRecvReduce>(
     337            0 :         neighborRank, recvLinkData, recvRemSlice, recvLocSrcSlice, recvLocDstSlice, dataType_, redOp_, dmaMode_);
     338              : 
     339            0 :     primGroup->Append(std::move(primRecvReduce));
     340              : 
     341              :     // SendReduce
     342            0 :     u64       sendOffset      = currSendReduceSlice.offset;
     343            0 :     u64       sendSize        = currSendReduceSlice.size;
     344            0 :     DataSlice sendLocSlice    = DataSlice(buffInfo_.inBuffType, sendOffset + buffInfo_.inBuffBaseOff, sendSize);
     345            0 :     DataSlice sendRemSrcSlice = DataSlice(buffInfo_.scratBuffType, sendOffset + buffInfo_.scratchBuffBaseOff, sendSize);
     346            0 :     DataSlice sendRemDstSlice = DataSlice(buffInfo_.inBuffType, sendOffset + buffInfo_.inBuffBaseOff, sendSize);
     347            0 :     std::unique_ptr<Primitive> primSendReduce = std::make_unique<PrimSendReduce>(
     348            0 :         neighborRank, sendLinkData, sendLocSlice, sendRemSrcSlice, sendRemDstSlice, dataType_, redOp_, dmaMode_);
     349              : 
     350            0 :     primGroup->Append(std::move(primSendReduce));
     351              : 
     352            0 :     return primGroup;
     353            0 : }
     354              : 
     355            0 : HcclResult TempReduceScatterMesh::PostCopyOffload(const RankSliceInfo     &sliceInfoVec,
     356              :                                                   std::vector<PrimQuePtr> &tempPrimQues)
     357              : {
     358            0 :     u64 srcOffset = sliceInfoVec[tempVirtRankMap_[myRank_]][0].offset;
     359            0 :     u64 srcSize   = sliceInfoVec[tempVirtRankMap_[myRank_]][0].size;
     360            0 :     u64 dstOffset = 0;
     361              : 
     362            0 :     DataSlice srcSlice = DataSlice(buffInfo_.inBuffType, srcOffset + buffInfo_.inBuffBaseOff, srcSize);
     363            0 :     DataSlice dstSlice = DataSlice(buffInfo_.outBuffType, dstOffset + buffInfo_.outBuffBaseOff, srcSize);
     364            0 :     std::unique_ptr<Primitive> primLocalCopy = std::make_unique<PrimLocalCopy>(srcSlice, dstSlice);
     365            0 :     tempPrimQues[0]->Append(std::move(primLocalCopy));
     366              : 
     367            0 :     return HcclResult::HCCL_SUCCESS;
     368            0 : }
     369              : } // namespace Hccl
        

Generated by: LCOV version 2.0-1