LCOV - code coverage report
Current view: top level - legacy/ascend950/unified_platform/resource/connection - dev_ub_connection.cc (source / functions) Coverage Total Hit
Test: coverage.info Lines: 73.3 % 682 500
Test Date: 2026-08-18 17:47:01 Functions: 79.2 % 77 61

            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 "dev_ub_connection.h"
      12              : 
      13              : #include <cstdlib>
      14              : 
      15              : #include "hccp_ctx.h"
      16              : #include "exception_util.h"
      17              : #include "rma_conn_exception.h"
      18              : #include "rdma_handle_manager.h"
      19              : #include "exchange_ub_conn_dto.h"
      20              : #include "env_config/env_config_v2.h"
      21              : 
      22              : namespace Hccl {
      23              : 
      24              : constexpr u32 OPBASED_UB_SQ_DEPTH_MAX = 8192;
      25              : constexpr u32 UB_SQ_OFFLOAD_DEPTH = 128;
      26              : constexpr u32 UB_SQ_WQEBB_SIZE = 64;
      27              : constexpr u32 WQE_NUM_PER_SQE = 4;                   // URMA约束每个SQE包含4个WQEBB
      28              : constexpr u32 UB_MAX_TRANS_SIZE = 256 * 1024 * 1024; // UB单次最大传输量256*1024*1024 Byte
      29              : 
      30          108 : DevUbConnection::DevUbConnection(
      31              :     const RdmaHandle rdmaHandle, const IpAddress& locAddr, const IpAddress& rmtAddr, const OpMode opMode,
      32              :     const bool devUsed, const HrtUbJfcMode jfcMode, const IpAddress& locIpv4Addr, const IpAddress& rmtIpv4Addr, u8 qos,
      33          108 :     CommEngine engine, u32 inSqDepth)
      34              :     : RmaConnection(nullptr, RmaConnType::UB),
      35          108 :       rdmaHandle(rdmaHandle),
      36          108 :       locAddr(locAddr),
      37          108 :       rmtAddr(rmtAddr),
      38          108 :       opMode(opMode),
      39          108 :       jfcMode(jfcMode),
      40          108 :       engine_(engine),
      41          108 :       locIpv4Addr(locIpv4Addr),
      42          108 :       rmtIpv4Addr(rmtIpv4Addr),
      43          108 :       rmtEid(rmtAddr.GetReverseEid()),
      44          108 :       locEid(locAddr.GetReverseEid()),
      45          108 :       qos_(qos),
      46          108 :       devUsed_(devUsed),
      47          216 :       sqDepth(inSqDepth)
      48              : {
      49          324 :     HCCL_INFO(
      50              :         "[DevUbConnection::DevUbConnection] rmtEid=%s, engine=%d", rmtEid.Describe().c_str(),
      51              :         static_cast<s32>(engine_));
      52          108 :     devLogicId = HrtGetDevice();
      53              : 
      54          108 :     auto dieIdAndFuncId = RdmaHandleManager::GetInstance().GetDieAndFuncId(rdmaHandle); // 获取dieId和FuncId
      55          108 :     dieId = dieIdAndFuncId.first;
      56          108 :     funcId = dieIdAndFuncId.second;
      57              : 
      58          108 :     if (engine_ == COMM_ENGINE_AIV) {
      59            1 :         CreateAivUrmaJfc();
      60          107 :     } else if (jfcMode == HrtUbJfcMode::USER_CTL) {
      61            0 :         jfcHandle = RdmaHandleManager::GetInstance().GetJfcHandleAndCqInfo(rdmaHandle, cqInfo_, jfcMode);
      62              :     } else {
      63          107 :         jfcHandle = RdmaHandleManager::GetInstance().GetJfcHandle(rdmaHandle, cqInfo_, jfcMode);
      64              :     }
      65          108 :     if (sqDepth == UB_SQ_DEPTH_NOT_SET) {
      66          106 :         sqDepth = OPBASED_UB_SQ_DEPTH_MAX;
      67          106 :         if (opMode == OpMode::OFFLOAD && !devUsed) {
      68            5 :             sqDepth = UB_SQ_OFFLOAD_DEPTH;
      69              :         }
      70              :     }
      71          324 :     HCCL_INFO(
      72              :         "[DevUbConnection][Constructor] sqDepth[%u], opMode[%d], devUsed[%d]", sqDepth, static_cast<s32>(opMode),
      73              :         devUsed);
      74              : 
      75          108 :     if (sqDepth > (UINT32_MAX / UB_SQ_WQEBB_SIZE / WQE_NUM_PER_SQE)) {
      76            0 :         THROW<InternalException>("integer overflow occurs");
      77              :     }
      78              : 
      79          108 :     if (!devUsed_) {
      80              :         // 注意:devUsed_=false 时 CreateJetty 在构造里同步执行,早于 InjectSharedJetty 调用,
      81              :         // 因此 isSharedJetty_ 此时还是 false,会走自建路径。当前共享 jetty 仅支持 AICPU
      82              :         // (devUsed_=true) 场景,构造里不会 CreateJetty,无影响。
      83              :         // TODO: 若将来支持 devUsed_=false 共享,需改为构造接受 sharedJetty 标志或延迟创建。
      84          106 :         CreateJetty(devUsed_);
      85              :     } else {
      86            6 :         HCCL_INFO("[DevUbConnection][Constructor] devUsed: defer CreateJetty until GetTpInfo maps qos.");
      87              :     }
      88          108 : }
      89              : 
      90            2 : DevUbTpConnection::DevUbTpConnection(
      91              :     const RdmaHandle rdmaHandle, const IpAddress& locAddr, const IpAddress& rmtAddr, const OpMode opMode,
      92              :     const bool devUsed, const HrtUbJfcMode jfcMode, const IpAddress& locIpv4Addr, const IpAddress& rmtIpv4Addr, u8 qos,
      93            2 :     CommEngine engine, u32 sqDepth)
      94              :     : DevUbConnection(
      95            2 :           rdmaHandle, locAddr, rmtAddr, opMode, devUsed, jfcMode, locIpv4Addr, rmtIpv4Addr, qos, engine, sqDepth)
      96              : {
      97            2 :     tpProtocol = TpProtocol::TP;
      98            2 : }
      99              : 
     100            4 : DevUbCtpConnection::DevUbCtpConnection(
     101              :     const RdmaHandle rdmaHandle, const IpAddress& locAddr, const IpAddress& rmtAddr, const OpMode opMode,
     102              :     const bool devUsed, const HrtUbJfcMode jfcMode, const IpAddress& locIpv4Addr, const IpAddress& rmtIpv4Addr, u8 qos,
     103            4 :     CommEngine engine, u32 sqDepth)
     104              :     : DevUbConnection(
     105            4 :           rdmaHandle, locAddr, rmtAddr, opMode, devUsed, jfcMode, locIpv4Addr, rmtIpv4Addr, qos, engine, sqDepth)
     106              : {
     107            4 :     tpProtocol = TpProtocol::CTP;
     108            4 : }
     109              : 
     110            0 : DevUbUboeConnection::DevUbUboeConnection(
     111              :     const RdmaHandle rdmaHandle, const IpAddress& locAddr, const IpAddress& rmtAddr, const OpMode opMode,
     112              :     const bool devUsed, const HrtUbJfcMode jfcMode, const IpAddress& locIpv4Addr, const IpAddress& rmtIpv4Addr, u8 qos,
     113            0 :     CommEngine engine)
     114            0 :     : DevUbConnection(rdmaHandle, locAddr, rmtAddr, opMode, devUsed, jfcMode, locIpv4Addr, rmtIpv4Addr, qos, engine)
     115              : {
     116            0 :     tpProtocol = TpProtocol::UBOE;
     117            0 :     jettyTimeOut = 16; // UBOE Jetty异步创建超时16秒
     118            0 : }
     119              : 
     120            1 : DevUbRtpConnection::DevUbRtpConnection(
     121              :     const RdmaHandle rdmaHandle, const IpAddress& locAddr, const IpAddress& rmtAddr, const OpMode opMode,
     122              :     const bool devUsed, const HrtUbJfcMode jfcMode, const IpAddress& locAddrEid, const IpAddress& rmtAddrEid, u8 qos,
     123            1 :     CommEngine engine, u32 sqDepth)
     124              :     : DevUbConnection(
     125            1 :           rdmaHandle, locAddr, rmtAddr, opMode, devUsed, jfcMode, locAddrEid, rmtAddrEid, qos, engine, sqDepth)
     126              : {
     127            1 :     tpProtocol = TpProtocol::UB_RTP;
     128              :     // UB_RTP与UBOE同属UB传输,Jetty异步创建超时一致,均为16秒
     129            1 :     jettyTimeOut = 16;
     130            1 : }
     131              : 
     132           47 : std::vector<char> DevUbConnection::GetUniqueId() const
     133              : {
     134           47 :     BinaryStream binaryStream;
     135           47 :     binaryStream << dieId;
     136           47 :     binaryStream << funcId;
     137           47 :     binaryStream << jettyId;
     138              : 
     139           47 :     u32 jfcPollMode = 0;          // 待修改,0代表STARS POLL,1代表software Poll
     140           47 :     bool dwqeCacheLocked = false; // 待修改,该jetty是否支持dwqeCachedLocked,默认不支持
     141           47 :     u64 sqCiAddr = 0; // 待修改,软件poll CQ情况下,需要AICPU从该地址中读取CI,依赖UB驱动支持
     142           47 :     binaryStream << jfcPollMode;
     143           47 :     binaryStream << dwqeCacheLocked;
     144           47 :     binaryStream << dbAddr;
     145           47 :     binaryStream << sqCiAddr;
     146           47 :     binaryStream << sqBuffVa;
     147           47 :     binaryStream << sqDepth;
     148           47 :     binaryStream << tpn;
     149           47 :     binaryStream << rmtEid.raw;
     150           47 :     binaryStream << locEid.raw;
     151           47 :     binaryStream << maxReadSize;
     152           47 :     binaryStream << maxWriteSize;
     153           47 :     binaryStream << static_cast<uint64_t>(jettyHandle);
     154              : 
     155           47 :     std::vector<char> result;
     156           47 :     binaryStream.Dump(result);
     157          141 :     HCCL_INFO("DevUbConnection::GetUniqueId:%s", Describe().c_str());
     158          141 :     HCCL_INFO(
     159              :         "type=%s, jfcPollMode=%u, dwqeCacheLocked=%d, sqCiAddr=0x%llx", rmaConnType.Describe().c_str(), jfcPollMode,
     160              :         dwqeCacheLocked, sqCiAddr);
     161           47 :     return result;
     162           47 : }
     163              : 
     164            0 : void DevUbConnection::SetCqInfo(HcclAiRMACQ& cq) const
     165              : {
     166            0 :     cq.jfcId = cqInfo_.id;
     167            0 :     cq.cqVA = cqInfo_.va;
     168            0 :     cq.cqeSize = cqInfo_.cqeSize;
     169            0 :     cq.cqDepth = cqInfo_.cqDepth;
     170            0 :     cq.dbAddr = cqInfo_.swdbAddr;
     171            0 : }
     172              : 
     173            0 : void DevUbConnection::SetWqInfo(HcclAiRMAWQ& wq) const
     174              : {
     175            0 :     wq.jettyId = jettyId;
     176            0 :     wq.dbAddr = dbAddr;
     177            0 :     wq.sqVA = sqBuffVa;
     178            0 :     wq.sqDepth = sqDepth * WQE_NUM_PER_SQE;
     179            0 :     wq.tp_id = tpn;
     180            0 :     memcpy_s(wq.rmtEid, sizeof(wq.rmtEid), rmtEid.raw, sizeof(wq.rmtEid));
     181            0 : }
     182              : 
     183            0 : void DevUbConnection::SetSqContextInfo(SqContext& sq) const
     184              : {
     185            0 :     sq.contextInfo.ubJfs.jfsID = jettyId;
     186            0 :     sq.contextInfo.ubJfs.dbVa = dbAddr;
     187            0 :     sq.contextInfo.ubJfs.sqVa = sqBuffVa;
     188            0 :     sq.contextInfo.ubJfs.sqDepth = sqDepth * WQE_NUM_PER_SQE;
     189            0 :     sq.contextInfo.ubJfs.tpID = tpn;
     190            0 :     memcpy_s(
     191            0 :         sq.contextInfo.ubJfs.remoteEID, sizeof(sq.contextInfo.ubJfs.remoteEID), rmtEid.raw,
     192              :         sizeof(sq.contextInfo.ubJfs.remoteEID));
     193            0 : }
     194              : 
     195            0 : void DevUbConnection::SetCqContextInfo(CqContext& cq) const
     196              : {
     197            0 :     cq.contextInfo.ubJfc.jfcID = cqInfo_.id;
     198            0 :     cq.contextInfo.ubJfc.scqVa = cqInfo_.va;
     199            0 :     cq.contextInfo.ubJfc.cqeSize = cqInfo_.cqeSize;
     200            0 :     cq.contextInfo.ubJfc.cqDepth = cqInfo_.cqDepth;
     201            0 :     cq.contextInfo.ubJfc.dbVa = cqInfo_.swdbAddr;
     202            0 : }
     203              : 
     204            0 : void DevUbConnection::Connect() { GetStatus(); }
     205              : 
     206            0 : inline uint32_t GetRandomNum()
     207              : {
     208            0 :     uint32_t randNum = std::rand();
     209            0 :     return randNum;
     210              : }
     211              : 
     212            1 : HcclResult DevUbConnection::CalcTotalTimeout(uint32_t& outTotalTimeoutMs)
     213              : {
     214            1 :     TpHandle tpHandle = tpInfo.tpHandle;
     215            1 :     uint32_t attrBitmap = 0;
     216            1 :     struct TpAttr tpAttr = {};
     217            1 :     u32 devicePhyId = HrtGetDevicePhyIdByIndex(devLogicId);
     218            4 :     CHK_RET(HrtRaGetTpAttrAsync(devicePhyId, rdmaHandle, tpHandle, attrBitmap, tpAttr, reqHandle));
     219            0 :     TpAttrInfo tpAttrInfo = TpAttrInfo(tpAttr);
     220            0 :     CHK_RET(TpManager::GetTpTotalTimeout(tpAttrInfo, outTotalTimeoutMs));
     221            0 :     return HCCL_SUCCESS;
     222              : }
     223              : 
     224            6 : void DevUbConnection::GetTimeOut() // 直接基于环境变量控制
     225              : {
     226            6 :     if (tpProtocol == TpProtocol::INVALID) { // 不感知tp建链,当前默认不支持
     227            0 :         HCCL_ERROR(
     228              :             "[DevUbConnection][%s] failed, tpProtocol[%s] is not expected.", __func__, tpProtocol.Describe().c_str());
     229            0 :         ThrowAbnormalStatus(std::string(__func__));
     230              :     }
     231              : 
     232            6 :     uint8_t envValue = static_cast<uint8_t>(EnvConfig::GetInstance().GetRdmaConfig().GetUbTimeOut());
     233            6 :     uint32_t envTimeOut = TpManager::TaHwValueToMs(envValue);
     234              : 
     235            6 :     if (tpProtocol == TpProtocol::CTP) {
     236            5 :         jettyTimeOut = envValue;
     237           15 :         HCCL_INFO("%s [UbCtp] Env Value [%u] (%ums).", __func__, envValue, envTimeOut);
     238            5 :         return;
     239              :     }
     240              : 
     241            1 :     if (tpProtocol == TpProtocol::UBOE || tpProtocol == TpProtocol::UB_RTP) {
     242            0 :         envValue = static_cast<uint8_t>(EnvConfig::GetInstance().GetRdmaConfig().GetUboeTimeOut());
     243            0 :         envTimeOut = TpManager::TaHwValueToMs(envValue);
     244            0 :         const char* tag = (tpProtocol == TpProtocol::UB_RTP) ? "[UB_RTP]" : "[UBoE]";
     245            0 :         HCCL_INFO("%s %s Env Value [%u] (%ums).", __func__, tag, envValue, envTimeOut);
     246              :     }
     247              : 
     248            1 :     uint32_t tpTimeOut = 0;
     249            1 :     CalcTotalTimeout(tpTimeOut);
     250            1 :     if (envTimeOut < tpTimeOut) {
     251              :         // 规则: 如果环境变量时间 < TP总超时,选择大于TP总超时的最小TA挡位
     252            0 :         jettyTimeOut = TpManager::FindMinTaHwValue(tpTimeOut);
     253            0 :         HCCL_WARNING(
     254              :             "%s Env timeout [%ums] < TP timeout [%ums]. Auto upgrade TA to hw_val[%u] (%ums).", __func__, envTimeOut,
     255              :             tpTimeOut, envValue, tpTimeOut);
     256              :     } else {
     257              :         // 规则: 否则,直接使用环境变量对应的挡位 (对齐到 0/8/16/24)
     258              :         // 注意:这里我们取环境变量所在挡位的基准值 (例如 env=10 -> 取 8)
     259            1 :         jettyTimeOut = envValue;
     260            3 :         HCCL_INFO(
     261              :             "%s Env timeout [%ums] >= TP timeout [%ums]. Use env gear base hw_val[%u] (%ums).", __func__, envTimeOut,
     262              :             tpTimeOut, envValue, envTimeOut);
     263              :     }
     264              : 
     265            3 :     HCCL_INFO("%s final TA Timeout [%u] (%ums).", __func__, jettyTimeOut, envTimeOut);
     266              : }
     267              : 
     268              : /*
     269              :  * UB 建链状态机(GetTpInfo/CreateJetty 异步未完成则停;同步成功时可同次推进):
     270              :  *   INIT                  --GetTpInfo fail--> TP_INFO_GETTING
     271              :  *   INIT / TP_INFO_GETTING --GetTpInfo ok--> CreateJetty --> JETTY_CREATING | JETTY_CREATED
     272              :  *                         (isSharedJetty_ 时跳过 CreateJetty,直接 JETTY_CREATED)
     273              :  *   JETTY_CREATING         --create done--> JETTY_CREATED (EXCHANGEABLE)
     274              :  *   JETTY_CREATED          --ImportRmtDto--> JETTY_IMPORTING(此处不推进)
     275              :  *   JETTY_IMPORTING        --import done--> READY
     276              :  */
     277           20 : RmaConnStatus DevUbConnection::GetStatus()
     278              : {
     279              :     // 稳定态 / 等待外部 ImportRmtDto:无需推进
     280           20 :     if (ubConnStatus == UbConnStatus::READY || ubConnStatus == UbConnStatus::JETTY_CREATED) {
     281            2 :         return status;
     282              :     }
     283              : 
     284           18 :     if (!CheckRequestResult()) {
     285            0 :         return status;
     286              :     }
     287              : 
     288           18 :     switch (ubConnStatus) {
     289            6 :         case UbConnStatus::INIT:
     290            6 :             ProcessInit();
     291            6 :             break;
     292            6 :         case UbConnStatus::TP_INFO_GETTING:
     293            6 :             if (!GetTpInfo()) {
     294            0 :                 break;
     295              :             }
     296            6 :             ProcessCreateJetty();
     297            6 :             break;
     298            1 :         case UbConnStatus::JETTY_CREATING:
     299            1 :             SetJettyInfo();
     300            1 :             status = RmaConnStatus::EXCHANGEABLE;
     301            1 :             ubConnStatus = UbConnStatus::JETTY_CREATED;
     302            1 :             break;
     303            4 :         case UbConnStatus::JETTY_IMPORTING:
     304            4 :             SetImportInfo();
     305            4 :             status = RmaConnStatus::READY;
     306            4 :             ubConnStatus = UbConnStatus::READY;
     307            4 :             break;
     308            1 :         default:
     309            2 :             ThrowAbnormalStatus(std::string(__func__));
     310            0 :             break;
     311              :     }
     312              : 
     313           17 :     return status;
     314              : }
     315              : 
     316            6 : void DevUbConnection::ProcessInit()
     317              : {
     318           18 :     HCCL_INFO(
     319              :         "[DevUbConnection][%s] start, status[%s], ubConnStatus[%s].", __func__, status.Describe().c_str(),
     320              :         ubConnStatus.Describe().c_str());
     321            6 :     if (!GetTpInfo()) {
     322            6 :         ubConnStatus = UbConnStatus::TP_INFO_GETTING;
     323            6 :         return;
     324              :     }
     325            0 :     ProcessCreateJetty();
     326              : }
     327              : 
     328            6 : void DevUbConnection::ProcessCreateJetty()
     329              : {
     330            6 :     GetTimeOut();
     331            6 :     if (isSharedJetty_) {
     332              :         // 共享 jetty:句柄已由 InjectSharedJetty 注入,跳过 CreateJetty
     333            0 :         status = RmaConnStatus::EXCHANGEABLE;
     334            0 :         ubConnStatus = UbConnStatus::JETTY_CREATED;
     335            0 :         HCCL_INFO("[DevUbConnection][%s] shared jetty mode, skip CreateJetty, direct to JETTY_CREATED.", __func__);
     336            0 :         return;
     337              :     }
     338            6 :     CreateJetty(devUsed_);
     339            6 :     if (devUsed_ || !CheckRequestResult()) {
     340            1 :         ubConnStatus = UbConnStatus::JETTY_CREATING;
     341            1 :         return;
     342              :     }
     343            5 :     SetJettyInfo();
     344            5 :     status = RmaConnStatus::EXCHANGEABLE;
     345            5 :     ubConnStatus = UbConnStatus::JETTY_CREATED;
     346              : }
     347              : 
     348            6 : std::unique_ptr<Serializable> DevUbConnection::GetExchangeDto()
     349              : {
     350            6 :     if (status != RmaConnStatus::READY && status != RmaConnStatus::EXCHANGEABLE) {
     351            0 :         HCCL_ERROR("[DevUbConnection][%s] status[%s] is not expected.", __func__, status.Describe().c_str());
     352            0 :         ThrowAbnormalStatus(std::string(__func__));
     353              :     }
     354              : 
     355            6 :     if (tpProtocol != TpProtocol::INVALID) {
     356            4 :         jettyImportCfg.localTpHandle = tpInfo.tpHandle;
     357              : 
     358           12 :         HCCL_INFO(
     359              :             "[DevUbConnection][%s] tpEnable, localTpHandle[0x%llx] localPsn[%u].", __func__,
     360              :             jettyImportCfg.localTpHandle, jettyImportCfg.localPsn);
     361              :     }
     362              : 
     363              :     std::unique_ptr<ExchangeUbConnDto> dto
     364            6 :         = make_unique<ExchangeUbConnDto>(tokenValue, keySize, jettyImportCfg.localTpHandle, jettyImportCfg.localPsn);
     365            6 :     (void)memcpy_s(dto->qpKey, HRT_UB_QP_KEY_MAX_LEN, localQpKey, HRT_UB_QP_KEY_MAX_LEN);
     366           12 :     return std::unique_ptr<Serializable>(dto.release());
     367            6 : }
     368              : 
     369            4 : void DevUbConnection::ParseRmtExchangeDto(const Serializable& rmtDto)
     370              : {
     371            4 :     auto dto = dynamic_cast<const ExchangeUbConnDto&>(rmtDto);
     372           12 :     HCCL_INFO("[DevUbConnection][%s] remoteConnDto[%s]", __func__, dto.Describe().c_str());
     373            4 :     remoteTokenValue = dto.tokenValue;
     374            4 :     (void)memcpy_s(remoteQpKey, HRT_UB_QP_KEY_MAX_LEN, dto.qpKey, HRT_UB_QP_KEY_MAX_LEN);
     375              : 
     376            4 :     if (tpProtocol != TpProtocol::INVALID) {
     377            4 :         jettyImportCfg.remoteTpHandle = dto.tpHandle;
     378            4 :         jettyImportCfg.remotePsn = dto.psn;
     379           12 :         HCCL_INFO(
     380              :             "[DevUbConnection][%s] tpEnable, remoteTpHandle[0x%llx], remotePsn[%u].", __func__,
     381              :             jettyImportCfg.remoteTpHandle, jettyImportCfg.remotePsn);
     382              :     }
     383            4 : }
     384              : 
     385            6 : void DevUbConnection::ImportRmtDto()
     386              : {
     387            6 :     if (ubConnStatus == UbConnStatus::READY) {
     388            3 :         HCCL_WARNING("[DevUbConnection][%s] import jetty already, %s.", __func__, Describe().c_str());
     389            1 :         return;
     390              :     }
     391              : 
     392            5 :     if (ubConnStatus != UbConnStatus::JETTY_CREATED) {
     393            0 :         HCCL_ERROR(
     394              :             "[DevUbConnection][%s] failed, ubConnStatus[%s] is not expected.", __func__,
     395              :             ubConnStatus.Describe().c_str());
     396            0 :         ThrowAbnormalStatus(std::string(__func__));
     397              :     }
     398              : 
     399            5 :     ImportJetty();
     400            5 :     ubConnStatus = UbConnStatus::JETTY_IMPORTING;
     401              : }
     402              : 
     403            2 : void DevUbConnection::ThrowAbnormalStatus(std::string funcName)
     404              : {
     405            2 :     auto errMsg = StringFormat("[DevUbConnection][%s] failed, [%s].", funcName.c_str(), Describe().c_str());
     406            2 :     status = RmaConnStatus::CONN_INVALID;
     407            2 :     ubConnStatus = UbConnStatus::CONN_INVALID;
     408            2 :     THROW<RmaConnException>(errMsg);
     409            2 : }
     410              : 
     411           23 : bool DevUbConnection::CheckRequestResult()
     412              : {
     413           23 :     if (reqHandle == 0) {
     414            7 :         return true;
     415              :     }
     416              : 
     417           16 :     ReqHandleResult result = HrtRaGetAsyncReqResult(reqHandle);
     418           16 :     if (result == ReqHandleResult::NOT_COMPLETED) {
     419            0 :         return false;
     420              :     }
     421              : 
     422           16 :     if (result != ReqHandleResult::COMPLETED) {
     423            0 :         THROW<InternalException>(
     424            0 :             "[DevUbConnection][%s] failed, result[%s] is unexpected.", __func__, result.Describe().c_str());
     425              :     }
     426              : 
     427           16 :     return true;
     428              : }
     429              : 
     430          114 : void DevUbConnection::CreateJetty(const bool devUsed)
     431              : {
     432          114 :     if (sqDepth > UINT32_MAX / UB_SQ_WQEBB_SIZE / WQE_NUM_PER_SQE) {
     433            0 :         THROW<InternalException>(
     434              :             "[DevUbConnection][%s] failed, sqDepth[%u] times "
     435              :             "UB_SQ_WQEBB_SIZE[%u] overflow uint32 max.",
     436              :             __func__, sqDepth, UB_SQ_WQEBB_SIZE);
     437              :     }
     438          114 :     u32 size = static_cast<u32>(sqDepth) * static_cast<u32>(UB_SQ_WQEBB_SIZE) * static_cast<u32>(WQE_NUM_PER_SQE);
     439              :     HrtRaUbCreateJettyParam req{
     440              :         jfcHandle,
     441              :         jfcHandle,
     442              :         GetUbToken(),
     443              :         0,
     444              :         HrtJettyMode::HOST_OPBASE, // 默认HOST单算子模式
     445              :         0,                         // HOST展开与AICPU展开传入jetty id为0,申请一个新的jetty
     446              :         0,                         // va由底层分配,此处填0即可。
     447              :         size,
     448              :         0,
     449              :         sqDepth,
     450          114 :         jettyTimeOut}; // 非CCUv2不需要填写sqeBufIndex
     451              : 
     452          114 :     if (opMode == OpMode::OFFLOAD) { // HOST展开图模式切换模式
     453            5 :         req.jettyMode = HrtJettyMode::HOST_OFFLOAD;
     454              :     }
     455              : 
     456          114 :     if (devUsed) { // AICPU场景切换模式
     457            1 :         req.jettyMode = HrtJettyMode::DEV_USED;
     458            3 :         HCCL_INFO("[DevUbConnection][%s] HrtJettyMode is DEV_USED.", __func__);
     459              :     }
     460              : 
     461          114 :     if (tpInfo.hasMappedJettyPriority) {
     462            2 :         req.qos = static_cast<u8>(tpInfo.mappedJettyPriority & 0xFU);
     463              :     }
     464          342 :     HCCL_INFO(
     465              :         "[DevUbConnection][%s] jetty create qos[%u] (maps to attr.ub.priority lower 4 bits).", __func__,
     466              :         static_cast<unsigned int>(req.qos));
     467              : 
     468          114 :     reqHandle = RaUbCreateJettyAsync(rdmaHandle, req, reqDataBuffer, jettyHandlePtr);
     469          114 : }
     470              : 
     471            0 : HcclResult DevUbConnection::InjectSharedJetty(
     472              :     Hccl::JettyHandle jettyHdl, void* jettyHdlPtr, uint32_t jId, uint64_t sqVa, uint64_t db, const uint8_t* qpKey,
     473              :     uint32_t kSize, uint32_t sDepth, uint64_t tpHdl, void* epTag, std::function<void(void*)> releaseCb)
     474              : {
     475            0 :     if (jettyHdl == 0 || jettyHdlPtr == nullptr || sDepth == 0) {
     476            0 :         HCCL_ERROR(
     477              :             "[DevUbConnection][%s] invalid params, jettyHdl[0x%llx], jettyHdlPtr[%p], sDepth[%u].", __func__,
     478              :             static_cast<unsigned long long>(jettyHdl), jettyHdlPtr, sDepth);
     479            0 :         return HCCL_E_PARA;
     480              :     }
     481              :     // 先做可能失败的 memcpy_s,成功后再设置共享模式相关状态,避免失败后析构重复调 releaseCb
     482            0 :     if (qpKey != nullptr && kSize > 0 && kSize <= HRT_UB_QP_KEY_MAX_LEN) {
     483            0 :         s32 ret = memcpy_s(&localQpKey[0], HRT_UB_QP_KEY_MAX_LEN, qpKey, kSize);
     484            0 :         if (ret != EOK) {
     485            0 :             HCCL_ERROR("[DevUbConnection][%s] memcpy_s localQpKey failed, ret[%d].", __func__, ret);
     486            0 :             return HCCL_E_INTERNAL;
     487              :         }
     488              :     }
     489            0 :     isSharedJetty_ = true;
     490            0 :     endpointTag_ = epTag;
     491            0 :     releaseCb_ = std::move(releaseCb);
     492            0 :     jettyHandle = jettyHdl;
     493            0 :     jettyHandlePtr = jettyHdlPtr;
     494            0 :     jettyId = jId;
     495            0 :     sqBuffVa = sqVa;
     496            0 :     dbAddr = db;
     497            0 :     keySize = kSize;
     498            0 :     sqDepth = sDepth;
     499              :     // 注入创建共享 jetty 时的 tpHandle,使主 connection 的 GetExchangeDto 发送与共享 jetty
     500              :     // 一致的 tpHandle,避免临时 connection 析构释放 HCCL TP 缓存后主 connection 重新申请
     501              :     // 得到不同 tpHandle,导致对端 import jetty 时 peerTpHandle 路由不匹配。
     502            0 :     tpInfo.tpHandle = tpHdl;
     503              :     // 注入后不直接跳状态机:仍需走 GetTpInfo 获取 TP 信息,由 ProcessCreateJetty
     504              :     // 中 isSharedJetty_ 分支跳过 CreateJetty 直接进入 JETTY_CREATED
     505            0 :     HCCL_INFO(
     506              :         "[DevUbConnection][%s] shared jetty injected, handle[0x%llx], jettyId[%u], sqDepth[%u], tpHandle[0x%llx].",
     507              :         __func__, static_cast<unsigned long long>(jettyHandle), jettyId, sqDepth,
     508              :         static_cast<unsigned long long>(tpInfo.tpHandle));
     509            0 :     return HCCL_SUCCESS;
     510              : }
     511              : 
     512            0 : void DevUbConnection::TransferJettyOwnership()
     513              : {
     514            0 :     isSharedJetty_ = true;
     515            0 :     HCCL_INFO(
     516              :         "[DevUbConnection][%s] jetty ownership transferred to Endpoint, handle[0x%llx].", __func__,
     517              :         static_cast<unsigned long long>(jettyHandle));
     518            0 : }
     519              : 
     520            0 : HcclResult DevUbConnection::GetJettyInfo(JettyInfo& info) const
     521              : {
     522            0 :     info.handle = jettyHandle;
     523            0 :     info.handlePtr = jettyHandlePtr;
     524            0 :     info.jettyId = jettyId;
     525            0 :     info.sqBuffVa = sqBuffVa;
     526            0 :     info.dbAddr = dbAddr;
     527            0 :     info.keySize = keySize;
     528            0 :     info.sqDepth = sqDepth;
     529            0 :     info.tpHandle = tpInfo.tpHandle;
     530            0 :     info.rdmaHandle = rdmaHandle;
     531            0 :     info.jfcHandle = jfcHandle;
     532            0 :     auto sRet = memcpy_s(&info.localQpKey[0], HRT_UB_QP_KEY_MAX_LEN, localQpKey, HRT_UB_QP_KEY_MAX_LEN);
     533            0 :     if (sRet != EOK) {
     534            0 :         HCCL_ERROR("[DevUbConnection][%s] memcpy_s failed, ret[%d].", __func__, sRet);
     535            0 :         return HCCL_E_INTERNAL;
     536              :     }
     537            0 :     return HCCL_SUCCESS;
     538              : }
     539              : 
     540            7 : void DevUbConnection::SetJettyInfo()
     541              : {
     542            7 :     struct QpCreateInfo* info = reinterpret_cast<QpCreateInfo*>(reqDataBuffer.data());
     543            7 :     jettyId = info->ub.id;
     544            7 :     jettyHandle = reinterpret_cast<JettyHandle>(jettyHandlePtr);
     545            7 :     keySize = info->key.size;
     546            7 :     sqBuffVa = info->ub.sqBuffVa; // hccp提供
     547           21 :     HCCL_RUN_INFO(
     548              :         "[DevUbConnection][%s] Get sqBuffVa is %llx. jettyId[%u], jettyHandle[%llx], dieId[%u], funcId[%u]", __func__,
     549              :         sqBuffVa, jettyId, jettyHandle, dieId, funcId);
     550              : 
     551            7 :     s32 ret = memcpy_s(&localQpKey[0], HRT_UB_QP_KEY_MAX_LEN, info->key.value, info->key.size);
     552            7 :     if (ret != 0) {
     553            0 :         THROW<InternalException>(StringFormat("[DevUbConnection][%s] memcpy_s failed, ret=%d", __func__, ret));
     554              :     }
     555              : 
     556            7 :     dbAddr = info->ub.dbAddr;
     557            7 : }
     558              : 
     559           12 : bool DevUbConnection::GetTpInfo()
     560              : {
     561           12 :     if (tpProtocol == TpProtocol::INVALID) { // 不感知tp建链,当前默认不支持
     562            0 :         HCCL_ERROR(
     563              :             "[DevUbConnection][%s] failed, tpProtocol[%s] is not expected.", __func__, tpProtocol.Describe().c_str());
     564            0 :         ThrowAbnormalStatus(std::string(__func__));
     565              :     }
     566              : 
     567              :     // 共享 jetty 模式:tpHandle 已由 InjectSharedJetty 注入(来自创建共享 jetty 的临时 connection),
     568              :     // 直接复用,不再向管控面重新申请。避免临时 connection 析构释放 HCCL TP 缓存后,主 connection
     569              :     // 重新申请得到不同 tpHandle,导致对端 import jetty 时 peerTpHandle 路由不匹配。
     570              :     // PSN 仍需本 connection 独立生成。
     571           12 :     if (isSharedJetty_ && tpInfo.tpHandle != 0) {
     572            0 :         GenerateLocalPsn();
     573            0 :         HCCL_INFO(
     574              :             "[DevUbConnection][%s] shared jetty mode, reuse injected tpHandle[0x%llx].", __func__,
     575              :             static_cast<unsigned long long>(tpInfo.tpHandle));
     576            0 :         return true;
     577              :     }
     578              : 
     579           12 :     RaUbGetTpInfoParam p{};
     580           12 :     p.locAddr = locAddr;
     581           12 :     p.rmtAddr = rmtAddr;
     582           12 :     p.tpProtocol = tpProtocol;
     583           12 :     p.qos = static_cast<uint32_t>(qos_);
     584           12 :     p.slLevelCount = 0;
     585           12 :     p.loopFirstTpLowestSl = false;
     586           12 :     p.locIpv4Addr = locIpv4Addr;
     587           12 :     p.rmtIpv4Addr = rmtIpv4Addr;
     588              : 
     589           12 :     auto ret = TpManager::GetInstance(devLogicId).GetTpInfo(p, tpInfo);
     590              : 
     591           12 :     switch (ret) {
     592            6 :         case HcclResult::HCCL_SUCCESS:
     593            6 :             GenerateLocalPsn();
     594            6 :             return true;
     595            6 :         case HcclResult::HCCL_E_AGAIN:
     596            6 :             return false;
     597            0 :         case HcclResult::HCCL_E_NOT_FOUND:
     598              :         default:
     599            0 :             HCCL_ERROR("[DevUbConnection][%s] failed, hccl result[%d]", __func__, ret);
     600            0 :             ThrowAbnormalStatus(std::string(__func__));
     601            0 :             break;
     602              :     }
     603            0 :     return true;
     604              : }
     605              : 
     606            6 : void DevUbConnection::GenerateLocalPsn() { jettyImportCfg.localPsn = GetRandomNum(); }
     607              : 
     608            5 : void DevUbConnection::ImportJetty()
     609              : {
     610            5 :     HrtRaUbJettyImportedInParam in{};
     611            5 :     in.key = remoteQpKey;
     612            5 :     in.keyLen = keySize;
     613            5 :     in.tokenValue = remoteTokenValue;
     614            5 :     in.jettyImportCfg = jettyImportCfg;
     615            5 :     in.jettyImportCfg.protocol = tpProtocol;
     616              : 
     617            7 :     if (tpProtocol != TpProtocol::CTP && tpProtocol != TpProtocol::TP && tpProtocol != TpProtocol::UBOE
     618            7 :         && tpProtocol != TpProtocol::UB_RTP) {
     619            0 :         HCCL_ERROR(
     620              :             "[DevUbConnection][%s] failed, tp protocol[%s] is not expected, %s.", __func__,
     621              :             tpProtocol.Describe().c_str(), Describe().c_str());
     622            0 :         ThrowAbnormalStatus(std::string(__func__));
     623              :     }
     624              : 
     625            5 :     reqHandle = RaUbTpImportJettyAsync(rdmaHandle, in, reqDataBuffer, remoteJettyHandlePtr);
     626            5 : }
     627              : 
     628            4 : void DevUbConnection::SetImportInfo()
     629              : {
     630            4 :     struct QpImportInfoT* info = reinterpret_cast<QpImportInfoT*>(reqDataBuffer.data());
     631            4 :     remoteJettyHandle = reinterpret_cast<TargetJettyHandle>(remoteJettyHandlePtr);
     632            4 :     tpn = info->out.ub.tpn;
     633            4 : }
     634              : 
     635          112 : void DevUbConnection::ReleaseTp()
     636              : {
     637          112 :     ReleaseUbConnectionTp(devLogicId, locAddr, rmtAddr, tpProtocol, tpInfo, static_cast<uint32_t>(qos_));
     638          112 : }
     639              : 
     640          110 : void DevUbConnection::ReleaseRemoteJettyIfImported(bool ctxValid)
     641              : {
     642          110 :     if (!rdmaHandle || remoteJettyHandle == 0) {
     643          110 :         return;
     644              :     }
     645            0 :     if (!ctxValid) {
     646            0 :         HCCL_WARNING(
     647              :             "[DevUbConnection][%s] skip HrtRaUbUnimportJetty, "
     648              :             "rdmaHandle=%p invalid (DeInit/DestroyAll done), remoteJettyHandle=0x%llx",
     649              :             __func__, rdmaHandle, static_cast<unsigned long long>(remoteJettyHandle));
     650              :     } else {
     651            0 :         HrtRaUbUnimportJetty(rdmaHandle, remoteJettyHandle);
     652              :     }
     653            0 :     remoteJettyHandle = 0;
     654              : }
     655              : 
     656            0 : void DevUbConnection::ReleaseSharedJettyModeResources(bool ctxValid)
     657              : {
     658              :     // 共享 jetty 模式:jetty 由 Endpoint::sharedJettyCtx_ 统一管理,connection 不销毁 jetty,
     659              :     // 但需通过 releaseCb_ 通知 Endpoint 减引用计数(引用归 0 时由 Endpoint 销毁 jetty)
     660              :     // 主 connection(InjectSharedJetty 路径,releaseCb_ 非空):构造函数创建的 JFC 从未被
     661              :     // CreateJetty 使用,安全销毁避免泄漏。
     662              :     // 临时 connection(TransferJettyOwnership 路径,releaseCb_ 为空):JFC 被 jetty 绑定使用,
     663              :     // 需等 Endpoint 销毁共享 jetty 后统一释放,不在此时销毁。
     664            0 :     if (releaseCb_ != nullptr && engine_ == COMM_ENGINE_AIV && jfcHandle != 0) {
     665            0 :         if (!ctxValid) {
     666            0 :             HCCL_WARNING(
     667              :                 "[DevUbConnection][%s] skip HrtRaUbDestroyJfc (shared), "
     668              :                 "rdmaHandle=%p invalid, jfcHandle=0x%llx",
     669              :                 __func__, rdmaHandle, static_cast<unsigned long long>(jfcHandle));
     670              :         } else {
     671            0 :             HrtRaUbDestroyJfc(rdmaHandle, jfcHandle);
     672              :         }
     673            0 :         jfcHandle = 0;
     674              :     }
     675            0 :     jettyHandle = 0;
     676            0 :     if (releaseCb_) {
     677            0 :         releaseCb_(endpointTag_);
     678            0 :         releaseCb_ = nullptr;
     679              :     }
     680            0 :     HCCL_INFO("[DevUbConnection][%s] shared jetty mode, skip DestroyJetty, releaseCb invoked.", __func__);
     681            0 : }
     682              : 
     683          110 : void DevUbConnection::ReleaseOwnedJettyAndJfc(bool ctxValid)
     684              : {
     685          110 :     if (jettyHandle != 0) {
     686            4 :         if (!ctxValid) {
     687           12 :             HCCL_WARNING(
     688              :                 "[DevUbConnection][%s] skip HrtRaUbDestroyJetty, "
     689              :                 "rdmaHandle=%p invalid, jettyHandle=0x%llx",
     690              :                 __func__, rdmaHandle, static_cast<unsigned long long>(jettyHandle));
     691              :         } else {
     692            0 :             HrtRaUbDestroyJetty(jettyHandle);
     693              :         }
     694            4 :         jettyHandle = 0;
     695              :     }
     696              : 
     697          110 :     if (engine_ == COMM_ENGINE_AIV && jfcHandle != 0) {
     698            0 :         if (!ctxValid) {
     699            0 :             HCCL_WARNING(
     700              :                 "[DevUbConnection][%s] skip HrtRaUbDestroyJfc, "
     701              :                 "rdmaHandle=%p invalid, jfcHandle=0x%llx",
     702              :                 __func__, rdmaHandle, static_cast<unsigned long long>(jfcHandle));
     703              :         } else {
     704            0 :             HrtRaUbDestroyJfc(rdmaHandle, jfcHandle);
     705              :         }
     706            0 :         jfcHandle = 0;
     707              :     }
     708          110 : }
     709              : 
     710          110 : void DevUbConnection::ReleaseResource()
     711              : {
     712          110 :     const bool ctxValid = (rdmaHandle != nullptr) && RdmaHandleManager::GetInstance().IsHandleValid(rdmaHandle);
     713              : 
     714          110 :     ReleaseRemoteJettyIfImported(ctxValid);
     715          110 :     ReleaseTp();
     716              : 
     717          110 :     if (isSharedJetty_) {
     718            0 :         ReleaseSharedJettyModeResources(ctxValid);
     719            0 :         return;
     720              :     }
     721              : 
     722          110 :     ReleaseOwnedJettyAndJfc(ctxValid);
     723              : }
     724              : 
     725            1 : void DevUbConnection::CreateAivUrmaJfc()
     726              : {
     727            1 :     jfcHandle = HrtRaUbCreateJfcUserCtl(rdmaHandle, cqInfo_);
     728            3 :     HCCL_INFO("[DevUbConnection][CreateAivUrmaJfc] create jfcHandle[%p] for rdmaHandle[%p].", jfcHandle, rdmaHandle);
     729            1 : }
     730              : 
     731          110 : DevUbConnection::~DevUbConnection() { DECTOR_TRY_CATCH("DevUbConnection", ReleaseResource()); }
     732              : 
     733              : // Suspend接口当前已不使用,由框架调用触发析构流程
     734            3 : bool DevUbConnection::Suspend()
     735              : {
     736            9 :     HCCL_WARNING("[DevUbConnection][%s] should not be called.", __func__);
     737            3 :     if (status == RmaConnStatus::SUSPENDED) {
     738            3 :         HCCL_INFO("[DevUbConnection][%s] RmaConnStatus is SUSPENDED, status[%s].", __func__, status.Describe().c_str());
     739            1 :         return true;
     740              :     }
     741              : 
     742            2 :     if (status != RmaConnStatus::READY) {
     743            2 :         ThrowAbnormalStatus(std::string(__func__));
     744              :     }
     745              : 
     746            1 :     ReleaseResource();
     747            1 :     status = RmaConnStatus::SUSPENDED;
     748            1 :     return true;
     749              : }
     750              : 
     751           15 : static void PrepareUbSendWrReqParamForWriteOrRead(
     752              :     HrtRaUbSendWrReqParam& sendWrReq, const HrtUbSendWrOpCode sendWrOpCode, const MemoryBuffer& remoteMemBuf,
     753              :     const MemoryBuffer& localMemBuf, JettyHandle remoteJettyHandle, const SqeConfig& config, u32 cqeEnable = 1)
     754              : {
     755           15 :     sendWrReq.cqeEn = cqeEnable;
     756           15 :     sendWrReq.opcode = sendWrOpCode;
     757           15 :     sendWrReq.size = localMemBuf.size;
     758           15 :     sendWrReq.localAddr = localMemBuf.addr;
     759           15 :     sendWrReq.remoteAddr = remoteMemBuf.addr;
     760              : 
     761           15 :     sendWrReq.lmemHandle = localMemBuf.memHandle;
     762           15 :     sendWrReq.rmemHandle = remoteMemBuf.memHandle;
     763           15 :     sendWrReq.handle = remoteJettyHandle;
     764              : 
     765              :     // 打印入参
     766           45 :     HCCL_INFO(
     767              :         "PrepareOneUbSendForRead params opCode=[%u], size=[%u], localAddr=[0x%llx], "
     768              :         "remoteAddr=[0x%llx], lmemHandle=[0x%llx], rmemHandle=[0x%llx], "
     769              :         "jettyHandle=[0x%llx], cqeEn=[%u], config=[%d]",
     770              :         static_cast<u32>(sendWrReq.opcode), sendWrReq.size, localMemBuf.addr, remoteMemBuf.addr, localMemBuf.memHandle,
     771              :         remoteMemBuf.memHandle, remoteJettyHandle, sendWrReq.cqeEn, config);
     772           15 : }
     773              : 
     774            9 : static void PrepareUbSendWrReqParamReduceInfo(HrtRaUbSendWrReqParam& sendWrReq, DataType dataType, ReduceOp reduceOp)
     775              : {
     776            9 :     sendWrReq.inlineReduceFlag = true;
     777            9 :     sendWrReq.dataType = dataType;
     778            9 :     sendWrReq.reduceOp = reduceOp;
     779           27 :     HCCL_INFO(
     780              :         "PrepareUbSendWrReqParamReduceInfo params inlineReduceFlag[%u], dataType[%s], reduceOp[%s]",
     781              :         sendWrReq.inlineReduceFlag, dataType.Describe().c_str(), reduceOp.Describe().c_str());
     782            9 : }
     783              : 
     784              : static void
     785            4 : PrepareUbSendWrReqParamNotifyInfo(HrtRaUbSendWrReqParam& sendWrReq, u64 data, const MemoryBuffer& remoteNotifyMemBuf)
     786              : {
     787            4 :     sendWrReq.opcode = HrtUbSendWrOpCode::WRITE_WITH_NOTIFY;
     788            4 :     sendWrReq.notifyData = data;
     789            4 :     sendWrReq.notifyAddr = remoteNotifyMemBuf.addr;
     790            4 :     sendWrReq.notifyHandle = remoteNotifyMemBuf.memHandle;
     791           12 :     HCCL_INFO(
     792              :         "PrepareUbSendWrReqParamNotifyInfo params opCode[%u], "
     793              :         "notifyData[0x%llx], notifyAddr[0x%llx], notifyHandle[0x%llx]",
     794              :         static_cast<u32>(sendWrReq.opcode), sendWrReq.notifyData, sendWrReq.notifyAddr, sendWrReq.notifyHandle);
     795            4 : }
     796              : 
     797              : std::unique_ptr<BaseTask>
     798           18 : DevUbConnection::ConstructTaskUbSend(const HrtRaUbSendWrRespParam& sendWrResp, const SqeConfig& config)
     799              : {
     800           18 :     unique_ptr<BaseTask> result;
     801           18 :     if (opMode == OpMode::OPBASE) {
     802           15 :         if (config.wqeMode == WqeMode::DWQE) {
     803            7 :             result = make_unique<TaskUbDirectSend>(
     804            7 :                 sendWrResp.funcId, sendWrResp.dieId, sendWrResp.jettyId, sendWrResp.dwqeSize, sendWrResp.dwqe);
     805            8 :         } else if (config.wqeMode == WqeMode::DB_SEND) {
     806              :             result
     807            7 :                 = make_unique<TaskUbDbSend>(sendWrResp.jettyId, sendWrResp.funcId, sendWrResp.piVal, sendWrResp.dieId);
     808            1 :         } else if (config.wqeMode == WqeMode::WRITE_VALUE) {
     809            3 :             HCCL_INFO("[DevUbConnection::%s] dbAddr=[%llx], piVal=[%u]", __func__, dbAddr, sendWrResp.piVal);
     810            1 :             result = make_unique<TaskWriteValue>(dbAddr, sendWrResp.piVal);
     811              :         } else {
     812            0 :             auto msg = StringFormat("Invalid WqeMode[%s]", config.wqeMode.Describe().c_str());
     813            0 :             THROW<InvalidParamsException>(msg);
     814            0 :         }
     815            3 :     } else if (opMode == OpMode::OFFLOAD) {
     816            8 :         CHK_PRT_THROW(
     817              :             sendWrResp.piVal < piVal,
     818              :             HCCL_ERROR(
     819              :                 "[DevUbConnection::%s] sendWrResp.piVal[%u] is less than piVal[%u]", __func__, sendWrResp.piVal, piVal),
     820              :             InvalidParamsException, "sendWrResp.piVal or piVal is invalid");
     821            2 :         u32 sendPiVal = sendWrResp.piVal - piVal;
     822            2 :         result = make_unique<TaskUbDbSend>(sendWrResp.jettyId, sendWrResp.funcId, sendPiVal, sendWrResp.dieId);
     823            6 :         HCCL_INFO(
     824              :             "[DevUbConnection::%s] sendPiVal[%u] piVal[%u] sendWrResp.piVal[%u]", __func__, sendPiVal, piVal,
     825              :             sendWrResp.piVal);
     826              :     } else {
     827            0 :         auto msg = StringFormat("Invalid OpMode[%s]", opMode.Describe().c_str());
     828            0 :         THROW<InvalidParamsException>(msg);
     829            0 :     }
     830              : 
     831           17 :     piVal = sendWrResp.piVal;
     832           17 :     return result;
     833            1 : }
     834              : 
     835           11 : void DevUbConnection::ProcessSlices(
     836              :     const MemoryBuffer& loc, const MemoryBuffer& rmt,
     837              :     std::function<void(const MemoryBuffer&, const MemoryBuffer&, u32)> processOneSlice, DataType dataType) const
     838              : {
     839           33 :     HCCL_INFO("[DevUbConnection::%s] start", __func__);
     840              : 
     841              :     // reduce操作需要保证切片大小是数据类型大小的整数倍
     842           11 :     u32 sliceSize = UB_MAX_TRANS_SIZE;
     843           11 :     if (dataType != DataType::INVALID) {
     844            7 :         u32 dataTypeSize = DATA_TYPE_SIZE_MAP.at(dataType);
     845            7 :         sliceSize = UB_MAX_TRANS_SIZE / dataTypeSize * dataTypeSize;
     846              :     }
     847              : 
     848           11 :     u32 locBufSize = loc.size;
     849           11 :     u32 sliceNum = locBufSize / sliceSize;
     850           11 :     u32 lastSliceSize = locBufSize % sliceSize;
     851           11 :     u64 totalSize = static_cast<u64>(sliceNum) * static_cast<u64>(sliceSize);
     852           11 :     if (loc.addr > UINT64_MAX - totalSize || rmt.addr > UINT64_MAX - totalSize) {
     853            0 :         THROW<InternalException>("integer overflow occurs");
     854              :     }
     855           11 :     for (u32 sliceIdx = 0; sliceIdx < sliceNum; sliceIdx++) {
     856            0 :         MemoryBuffer locSlice(loc.addr + sliceIdx * sliceSize, sliceSize, loc.memHandle);
     857            0 :         MemoryBuffer rmtSlice(rmt.addr + sliceIdx * sliceSize, sliceSize, rmt.memHandle);
     858              :         // 当前是最后一片,且没有lastSlice时,启用cqe
     859            0 :         u32 cqeEnable = (sliceIdx == sliceNum - 1 && lastSliceSize == 0) ? 1 : 0;
     860            0 :         processOneSlice(locSlice, rmtSlice, cqeEnable);
     861              :     }
     862              : 
     863           11 :     if (lastSliceSize > 0) {
     864           11 :         MemoryBuffer lastLocSlice(loc.addr + sliceNum * sliceSize, lastSliceSize, loc.memHandle);
     865           11 :         MemoryBuffer lastRmtSlice(rmt.addr + sliceNum * sliceSize, lastSliceSize, rmt.memHandle);
     866           11 :         processOneSlice(lastLocSlice, lastRmtSlice, 1);
     867           11 :         sliceNum++;
     868              :     }
     869              : 
     870           33 :     HCCL_INFO(
     871              :         "[DevUbConnection::%s] end, locBufSize[%u], sliceNUm[%u], sliceSize[%u], lastSliceSize[%u]", __func__,
     872              :         locBufSize, sliceNum, sliceSize, lastSliceSize);
     873           11 : }
     874              : 
     875            4 : void DevUbConnection::ProcessSlicesWithNotify(
     876              :     const MemoryBuffer& loc, const MemoryBuffer& rmt,
     877              :     std::function<void(const MemoryBuffer&, const MemoryBuffer&, u32)> processOneSlice,
     878              :     std::function<void(const MemoryBuffer&, const MemoryBuffer&)> processOneSliceWithNotify, DataType dataType) const
     879              : {
     880           12 :     HCCL_INFO("[DevUbConnection::%s] start", __func__);
     881              : 
     882              :     // reduce操作需要保证切片大小是数据类型大小的整数倍
     883            4 :     u32 sliceSize = UB_MAX_TRANS_SIZE;
     884            4 :     if (dataType != DataType::INVALID) {
     885            2 :         u32 dataTypeSize = DATA_TYPE_SIZE_MAP.at(dataType);
     886            2 :         sliceSize = UB_MAX_TRANS_SIZE / dataTypeSize * dataTypeSize;
     887              :     }
     888              : 
     889            4 :     u32 locBufSize = loc.size;
     890            4 :     u32 sliceNum = locBufSize / sliceSize;
     891            4 :     u32 lastSliceSize = locBufSize % sliceSize;
     892            4 :     if (sliceNum > 0 && lastSliceSize == 0) {
     893            0 :         sliceNum--;
     894            0 :         lastSliceSize = sliceSize;
     895              :     }
     896              : 
     897            4 :     for (u32 sliceIdx = 0; sliceIdx < sliceNum; sliceIdx++) {
     898            0 :         MemoryBuffer locSlice(loc.addr + sliceIdx * sliceSize, sliceSize, loc.memHandle);
     899            0 :         MemoryBuffer rmtSlice(rmt.addr + sliceIdx * sliceSize, sliceSize, rmt.memHandle);
     900              :         // 固定会有lastSlice,则前面的cqe都不启用
     901            0 :         processOneSlice(locSlice, rmtSlice, 0);
     902              :     }
     903              : 
     904            4 :     if (lastSliceSize > 0) {
     905            4 :         MemoryBuffer lastLocSlice(loc.addr + sliceNum * sliceSize, lastSliceSize, loc.memHandle);
     906            4 :         MemoryBuffer lastRmtSlice(rmt.addr + sliceNum * sliceSize, lastSliceSize, rmt.memHandle);
     907            4 :         processOneSliceWithNotify(lastLocSlice, lastRmtSlice);
     908            4 :         sliceNum++;
     909              :     }
     910              : 
     911           12 :     HCCL_INFO(
     912              :         "[DevUbConnection::%s] end, locBufSize[%u], sliceNum[%u], sliceSize[%u], lastSliceSize[%u]", __func__,
     913              :         locBufSize, sliceNum, sliceSize, lastSliceSize);
     914            4 : }
     915              : 
     916              : unique_ptr<BaseTask>
     917            2 : DevUbConnection::PrepareRead(const MemoryBuffer& remoteMemBuf, const MemoryBuffer& localMemBuf, const SqeConfig& config)
     918              : {
     919            2 :     VerifySizeIsEqual(remoteMemBuf, localMemBuf, "DevUbConnection::PrepareRead");
     920              : 
     921            2 :     if (localMemBuf.size == 0) {
     922            0 :         return nullptr;
     923              :     }
     924              : 
     925            2 :     HrtRaUbSendWrRespParam sendWrResp{};
     926            2 :     ProcessSlices(
     927            2 :         localMemBuf, remoteMemBuf, [&](const MemoryBuffer& locSlice, const MemoryBuffer& rmtSlice, u32 cqeEnable) {
     928            2 :             HrtRaUbSendWrReqParam sendWrReq = {};
     929            2 :             PrepareUbSendWrReqParamForWriteOrRead(
     930              :                 sendWrReq, HrtUbSendWrOpCode::READ, rmtSlice, locSlice, remoteJettyHandle, config, cqeEnable);
     931              : 
     932            2 :             sendWrResp = HrtRaUbPostSend(jettyHandle, sendWrReq);
     933            2 :         });
     934              : 
     935            2 :     return ConstructTaskUbSend(sendWrResp, config);
     936              : }
     937              : 
     938            2 : unique_ptr<BaseTask> DevUbConnection::PrepareReadReduce(
     939              :     const MemoryBuffer& remoteMemBuf, const MemoryBuffer& localMemBuf, DataType dataType, ReduceOp reduceOp,
     940              :     const SqeConfig& config)
     941              : {
     942            2 :     VerifySizeIsEqual(remoteMemBuf, localMemBuf, "DevUbConnection::PrepareReadReduce");
     943              : 
     944            2 :     if (localMemBuf.size == 0) {
     945            0 :         return nullptr;
     946              :     }
     947              : 
     948            2 :     HrtRaUbSendWrRespParam sendWrResp{};
     949            2 :     ProcessSlices(
     950              :         localMemBuf, remoteMemBuf,
     951            2 :         [&](const MemoryBuffer& locSlice, const MemoryBuffer& rmtSlice, u32 cqeEnable) {
     952            2 :             HrtRaUbSendWrReqParam sendWrReq = {};
     953            2 :             PrepareUbSendWrReqParamForWriteOrRead(
     954              :                 sendWrReq, HrtUbSendWrOpCode::READ, rmtSlice, locSlice, remoteJettyHandle, config, cqeEnable);
     955            2 :             PrepareUbSendWrReqParamReduceInfo(sendWrReq, dataType, reduceOp);
     956              : 
     957            2 :             sendWrResp = HrtRaUbPostSend(jettyHandle, sendWrReq);
     958            2 :         },
     959              :         dataType);
     960              : 
     961            2 :     return ConstructTaskUbSend(sendWrResp, config);
     962              : }
     963              : 
     964            6 : unique_ptr<BaseTask> DevUbConnection::PrepareWrite(
     965              :     const MemoryBuffer& remoteMemBuf, const MemoryBuffer& localMemBuf, const SqeConfig& config)
     966              : {
     967            8 :     VerifySizeIsEqual(remoteMemBuf, localMemBuf, "DevUbConnection::PrepareWrite");
     968              : 
     969            4 :     if (localMemBuf.size == 0) {
     970            2 :         return nullptr;
     971              :     }
     972              : 
     973            2 :     HrtRaUbSendWrRespParam sendWrResp{};
     974            2 :     ProcessSlices(
     975            2 :         localMemBuf, remoteMemBuf, [&](const MemoryBuffer& locSlice, const MemoryBuffer& rmtSlice, u32 cqeEnable) {
     976            2 :             HrtRaUbSendWrReqParam sendWrReq = {};
     977            2 :             PrepareUbSendWrReqParamForWriteOrRead(
     978              :                 sendWrReq, HrtUbSendWrOpCode::WRITE, rmtSlice, locSlice, remoteJettyHandle, config, cqeEnable);
     979            2 :             sendWrResp = HrtRaUbPostSend(jettyHandle, sendWrReq);
     980            2 :         });
     981              : 
     982            2 :     return ConstructTaskUbSend(sendWrResp, config);
     983              : }
     984              : 
     985            7 : unique_ptr<BaseTask> DevUbConnection::PrepareWriteReduce(
     986              :     const MemoryBuffer& remoteMemBuf, const MemoryBuffer& localMemBuf, DataType dataType, ReduceOp reduceOp,
     987              :     const SqeConfig& config)
     988              : {
     989            8 :     VerifySizeIsEqual(remoteMemBuf, localMemBuf, "DevUbConnection::PrepareWriteReduce");
     990              : 
     991            6 :     if (localMemBuf.size == 0) {
     992            1 :         return nullptr;
     993              :     }
     994              : 
     995            5 :     HrtRaUbSendWrRespParam sendWrResp{};
     996            5 :     ProcessSlices(
     997              :         localMemBuf, remoteMemBuf,
     998            5 :         [&](const MemoryBuffer& locSlice, const MemoryBuffer& rmtSlice, u32 cqeEnable) {
     999            5 :             HrtRaUbSendWrReqParam sendWrReq = {};
    1000            5 :             PrepareUbSendWrReqParamForWriteOrRead(
    1001              :                 sendWrReq, HrtUbSendWrOpCode::WRITE, rmtSlice, locSlice, remoteJettyHandle, config, cqeEnable);
    1002            5 :             PrepareUbSendWrReqParamReduceInfo(sendWrReq, dataType, reduceOp);
    1003            5 :             sendWrResp = HrtRaUbPostSend(jettyHandle, sendWrReq);
    1004            5 :         },
    1005              :         dataType);
    1006              : 
    1007            5 :     return ConstructTaskUbSend(sendWrResp, config);
    1008              : }
    1009              : 
    1010              : unique_ptr<BaseTask>
    1011            3 : DevUbConnection::PrepareInlineWrite(const MemoryBuffer& remoteMemBuf, u64 data, const SqeConfig& config)
    1012              : {
    1013            3 :     HrtRaUbSendWrReqParam sendWrReq = {};
    1014            3 :     sendWrReq.opcode = HrtUbSendWrOpCode::WRITE;
    1015            3 :     sendWrReq.remoteAddr = remoteMemBuf.addr;
    1016            3 :     sendWrReq.rmemHandle = remoteMemBuf.memHandle;
    1017            3 :     sendWrReq.handle = remoteJettyHandle;
    1018            3 :     sendWrReq.inlineFlag = true;
    1019            3 :     sendWrReq.inlineData = reinterpret_cast<u8*>(&data);
    1020            3 :     sendWrReq.size = sizeof(data);
    1021              :     /*
    1022              :      * 当前只有前后同步使用writeValue任务
    1023              :      * 由于writeValue任务不使能cqe,
    1024              :      * writeValue和dwqe混用会有潜在问题,所以后面需要区分开这两种任务模式
    1025              :      * 不在同一个connection里面既使用writeValue又使用dwqe
    1026              :      */
    1027            3 :     if (config.wqeMode == WqeMode::WRITE_VALUE && opMode == OpMode::OPBASE) {
    1028              :         // 当前只有inlineWrite使用write value
    1029              :         // 图模式不能使用writeValue
    1030              :         // writeValue 不需要使能cqe
    1031            1 :         sendWrReq.cqeEn = false;
    1032              :     }
    1033              : 
    1034            9 :     HCCL_INFO(
    1035              :         "DevUbConnection::PrepareInlineWrite params opCode=[%u], "
    1036              :         "remoteAddr=[0x%llx], rmemHandle=[0x%llx], remoteJettyHandle=[0x%llx], inlineFlag[%u], size=[%u], data=[%u]",
    1037              :         sendWrReq.opcode, sendWrReq.remoteAddr, sendWrReq.rmemHandle, sendWrReq.handle, sendWrReq.inlineFlag,
    1038              :         sendWrReq.size, static_cast<u32>(*sendWrReq.inlineData));
    1039            3 :     auto res = HrtRaUbPostSend(jettyHandle, sendWrReq);
    1040              : 
    1041            6 :     return ConstructTaskUbSend(res, config);
    1042              : }
    1043              : 
    1044              : inline HrtRaUbSendWrReqParam ConstructUbSendWrReqParamForWriteWithNotify(
    1045              :     const MemoryBuffer& remoteMemBuf, const MemoryBuffer& localMemBuf, u64 data, const MemoryBuffer& remoteNotifyMemBuf)
    1046              : {
    1047              :     HrtRaUbSendWrReqParam sendWrReq = {};
    1048              :     sendWrReq.opcode = HrtUbSendWrOpCode::WRITE_WITH_NOTIFY;
    1049              :     sendWrReq.size = remoteMemBuf.size;
    1050              :     sendWrReq.localAddr = localMemBuf.addr;
    1051              :     sendWrReq.remoteAddr = remoteMemBuf.addr;
    1052              :     sendWrReq.lmemHandle = localMemBuf.memHandle;
    1053              :     sendWrReq.rmemHandle = remoteMemBuf.memHandle;
    1054              :     sendWrReq.notifyData = data;
    1055              :     sendWrReq.notifyAddr = remoteNotifyMemBuf.addr;
    1056              :     sendWrReq.notifyHandle = remoteNotifyMemBuf.memHandle;
    1057              : 
    1058              :     return sendWrReq;
    1059              : }
    1060              : 
    1061            2 : unique_ptr<BaseTask> DevUbConnection::PrepareWriteWithNotify(
    1062              :     const MemoryBuffer& remoteMemBuf, const MemoryBuffer& localMemBuf, u64 data, const MemoryBuffer& remoteNotifyMemBuf,
    1063              :     const SqeConfig& config)
    1064              : {
    1065            2 :     VerifySizeIsEqual(remoteMemBuf, localMemBuf, "DevUbConnection::PrepareWriteWithNotify");
    1066              : 
    1067            2 :     if (localMemBuf.size == 0) {
    1068            0 :         return nullptr;
    1069              :     }
    1070              : 
    1071            2 :     HrtRaUbSendWrRespParam sendWrResp{};
    1072            2 :     ProcessSlicesWithNotify(
    1073              :         localMemBuf, remoteMemBuf,
    1074            4 :         [&](const MemoryBuffer& locSlice, const MemoryBuffer& rmtSlice, u32 cqeEnable) {
    1075            0 :             HrtRaUbSendWrReqParam sendWrReq = {};
    1076            0 :             PrepareUbSendWrReqParamForWriteOrRead(
    1077              :                 sendWrReq, HrtUbSendWrOpCode::WRITE, rmtSlice, locSlice, remoteJettyHandle, config, cqeEnable);
    1078            0 :             sendWrResp = HrtRaUbPostSend(jettyHandle, sendWrReq);
    1079            0 :         },
    1080            2 :         [&](const MemoryBuffer& locSlice, const MemoryBuffer& rmtSlice) {
    1081            2 :             HrtRaUbSendWrReqParam sendWrReq = {};
    1082            2 :             PrepareUbSendWrReqParamForWriteOrRead(
    1083              :                 sendWrReq, HrtUbSendWrOpCode::WRITE, rmtSlice, locSlice, remoteJettyHandle, config);
    1084            2 :             PrepareUbSendWrReqParamNotifyInfo(sendWrReq, data, remoteNotifyMemBuf);
    1085              : 
    1086            2 :             sendWrResp = HrtRaUbPostSend(jettyHandle, sendWrReq);
    1087            2 :         });
    1088              : 
    1089            2 :     return ConstructTaskUbSend(sendWrResp, config);
    1090              : }
    1091              : 
    1092            2 : unique_ptr<BaseTask> DevUbConnection::PrepareWriteReduceWithNotify(
    1093              :     const MemoryBuffer& remoteMemBuf, const MemoryBuffer& localMemBuf, DataType dataType, ReduceOp reduceOp, u64 data,
    1094              :     const MemoryBuffer& remoteNotifyMemBuf, const SqeConfig& config)
    1095              : {
    1096            2 :     VerifySizeIsEqual(remoteMemBuf, localMemBuf, "DevUbConnection::PrepareWriteReduceWithNotify");
    1097              : 
    1098            2 :     if (localMemBuf.size == 0) {
    1099            0 :         return nullptr;
    1100              :     }
    1101              : 
    1102            2 :     HrtRaUbSendWrRespParam sendWrResp{};
    1103            2 :     ProcessSlicesWithNotify(
    1104              :         localMemBuf, remoteMemBuf,
    1105            4 :         [&](const MemoryBuffer& locSlice, const MemoryBuffer& rmtSlice, u32 cqeEnable) {
    1106            0 :             HrtRaUbSendWrReqParam sendWrReq = {};
    1107            0 :             PrepareUbSendWrReqParamForWriteOrRead(
    1108              :                 sendWrReq, HrtUbSendWrOpCode::WRITE, rmtSlice, locSlice, remoteJettyHandle, config, cqeEnable);
    1109            0 :             PrepareUbSendWrReqParamReduceInfo(sendWrReq, dataType, reduceOp);
    1110            0 :             sendWrResp = HrtRaUbPostSend(jettyHandle, sendWrReq);
    1111            0 :         },
    1112            2 :         [&](const MemoryBuffer& locSlice, const MemoryBuffer& rmtSlice) {
    1113            2 :             HrtRaUbSendWrReqParam sendWrReq = {};
    1114            2 :             PrepareUbSendWrReqParamForWriteOrRead(
    1115              :                 sendWrReq, HrtUbSendWrOpCode::WRITE, rmtSlice, locSlice, remoteJettyHandle, config);
    1116            2 :             PrepareUbSendWrReqParamReduceInfo(sendWrReq, dataType, reduceOp);
    1117            2 :             PrepareUbSendWrReqParamNotifyInfo(sendWrReq, data, remoteNotifyMemBuf);
    1118            2 :             sendWrResp = HrtRaUbPostSend(jettyHandle, sendWrReq);
    1119            2 :         },
    1120              :         dataType);
    1121              : 
    1122            2 :     return ConstructTaskUbSend(sendWrResp, config);
    1123              : }
    1124              : 
    1125          150 : string DevUbConnection::Describe() const
    1126              : {
    1127              :     return StringFormat(
    1128              :         "DevUbConnection[locAddr=%s, rmtAddr=%s, status=%s, dieId=%u, funcId=%u, jettyId=%u, sqBuffVa=%llx, "
    1129              :         "sqDepth=%u, maxReadSize=%u, maxWriteSize=%u, tpn=%u, dbAddr=0x%llx]",
    1130          450 :         locAddr.Describe().c_str(), rmtAddr.Describe().c_str(), status.Describe().c_str(), dieId, funcId, jettyId,
    1131          600 :         sqBuffVa, sqDepth, maxReadSize, maxWriteSize, tpn, dbAddr);
    1132              : }
    1133              : 
    1134            1 : HcclResult DevUbConnection::Describe(std::string& dfxMsg)
    1135              : {
    1136            1 :     uint16_t udpSport = 0xFFFF; // 无法获取实际的udpSport,使用0xFFFF表示未知
    1137            1 :     if (tpProtocol == TpProtocol::TP) {
    1138            1 :         struct TpAttr tpAttr {};
    1139            1 :         uint32_t attrBitmap = 1 << 13; // 13对应dataUdpSrcport
    1140            1 :         TRY_CATCH_PRINT_ERROR(
    1141              :             u32 devicePhyId = HrtGetDevicePhyIdByIndex(devLogicId);
    1142              :             HcclResult ret
    1143              :             = HrtRaGetTpAttrAsync(devicePhyId, rdmaHandle, tpInfo.tpHandle, attrBitmap, tpAttr, reqHandle);
    1144              :             if (ret == HCCL_E_NOT_SUPPORT) {
    1145              :                 HCCL_ERROR(
    1146              :                     "[DevUbConnection::%s] this package does not support RaGetTpAttrAsync for device,"
    1147              :                     " please change new package, devPhyId[%u]",
    1148              :                     __func__, devicePhyId);
    1149              :                 return ret;
    1150              :             } else if (ret != HCCL_SUCCESS) {
    1151              :                 HCCL_ERROR("[DevUbConnection::%s] failed, hccl result[%d]", __func__, ret);
    1152              :                 return ret;
    1153              :             });
    1154            1 :         udpSport = tpAttr.dataUdpSrcport;
    1155              :     }
    1156            1 :     udpSport = udpSport & 0xFF;
    1157              : 
    1158              :     std::string dfxStr = StringFormat(
    1159              :         "chip id[%u] die id[%u] func id[%u] jetty id[%u] "
    1160              :         "local %s remote %s udp sport[%u]",
    1161            1 :         devLogicId, dieId, funcId, jettyId, locEid.Describe().c_str(), rmtEid.Describe().c_str(), udpSport);
    1162            1 :     dfxMsg += dfxStr;
    1163            3 :     HCCL_INFO("[DevUbConnection::%s] %s", __func__, dfxStr.c_str());
    1164            1 :     return HCCL_SUCCESS;
    1165            1 : }
    1166              : 
    1167            4 : void DevUbConnection::AddNop(const Stream& stream)
    1168              : {
    1169            4 :     if (opMode != OpMode::OFFLOAD) {
    1170            3 :         HCCL_WARNING("[DevUbConnection][AddNop]Invalid OpMode[%s]", opMode.Describe().c_str());
    1171            1 :         return;
    1172              :     }
    1173            3 :     if (sqDepth < piVal) {
    1174            1 :         auto msg = StringFormat("Invalid piVal[%u], piVal should be less than or equal to sqDepth[%u]", piVal, sqDepth);
    1175            1 :         THROW<InvalidParamsException>(msg);
    1176            1 :     }
    1177            2 :     if (sqDepth == piVal) {
    1178            0 :         return;
    1179              :     }
    1180            2 :     u32 numNop = sqDepth - piVal;
    1181            2 :     HrtRaUbPostNops(jettyHandle, remoteJettyHandle, numNop);
    1182              : 
    1183              :     HrtUbDbInfo info;
    1184            2 :     info.dbNum = 1;
    1185            2 :     info.wrCqe = 0; // 默认值是0 不会cqe  如果传1,驱动分发,会给hccl cqe,用于维护ci指针。
    1186            2 :     info.info[0].functionId = funcId;
    1187            2 :     info.info[0].dieId = dieId;
    1188            2 :     info.info[0].jettyId = jettyId;
    1189            2 :     info.info[0].piValue = numNop;
    1190            2 :     HrtUbDbSend(info, stream.GetPtr());
    1191              : 
    1192            2 :     piVal = sqDepth;
    1193              : }
    1194              : 
    1195            4 : HrtUbJfcMode DevUbConnection::GetUbJfcMode() const { return jfcMode; }
    1196              : 
    1197            5 : JettyHandle& DevUbConnection::GetJettyHandle() { return jettyHandle; }
    1198              : 
    1199            2 : JettyHandle& DevUbConnection::GetRemoteJettyHandle() { return remoteJettyHandle; }
    1200              : 
    1201            2 : RdmaHandle& DevUbConnection::GetRdmaHandle() { return rdmaHandle; }
    1202              : 
    1203            6 : u32 DevUbConnection::GetPiVal() const { return piVal; }
    1204              : 
    1205            5 : u32 DevUbConnection::GetCiVal() const { return ciVal; }
    1206              : 
    1207            5 : u32 DevUbConnection::GetSqDepth() const { return sqDepth; }
    1208              : 
    1209            2 : void DevUbConnection::UpdateCiVal(u32 ci) { ciVal = ci; }
    1210              : 
    1211            7 : std::vector<DevUbConnection*> GetStarsPollUbConns(const std::vector<RmaConnection*>& rmaConns)
    1212              : {
    1213            7 :     std::vector<DevUbConnection*> ubConns;
    1214            8 :     for (auto& rmaConn : rmaConns) {
    1215            1 :         if (rmaConn->GetRmaConnType() == RmaConnType::UB) {
    1216            1 :             if (dynamic_cast<DevUbConnection*>(rmaConn)->GetUbJfcMode() == HrtUbJfcMode::STARS_POLL) {
    1217            1 :                 ubConns.emplace_back(dynamic_cast<DevUbConnection*>(rmaConn));
    1218              :             }
    1219              :         }
    1220              :     }
    1221            7 :     return ubConns;
    1222            0 : }
    1223              : 
    1224            7 : bool IfNeedUpdatingUbCi(const std::vector<DevUbConnection*>& ubConns)
    1225              : {
    1226            9 :     for (auto& ubConn : ubConns) {
    1227            2 :         u32 pi = ubConn->GetPiVal();
    1228            2 :         u32 ci = ubConn->GetCiVal();
    1229            2 :         u32 sqDepth = ubConn->GetSqDepth();
    1230              :         // 考虑pi翻转场景
    1231            2 :         u32 extra = pi >= ci ? 0 : sqDepth;
    1232            2 :         constexpr u32 thresholdDivisor = 2;
    1233              : 
    1234            2 :         if (static_cast<double>(pi + extra - ci)
    1235            2 :             >= static_cast<double>(sqDepth) / thresholdDivisor) { // 当pi和ci差距大于sqDepth/2时,更新ci
    1236            0 :             return true;
    1237              :         }
    1238              :     }
    1239            7 :     return false;
    1240              : }
    1241              : 
    1242            0 : void DevUbConnection::SetMaxReadSize(u32 value) { maxReadSize = value; }
    1243              : 
    1244            0 : void DevUbConnection::SetMaxWriteSize(u32 value) { maxWriteSize = value; }
    1245              : 
    1246              : } // namespace Hccl
        

Generated by: LCOV version 2.0-1