LCOV - code coverage report
Current view: top level - server/config - config_info_operator.cpp (source / functions) Coverage Total Hit
Test: coverage.info Lines: 89.9 % 943 848
Test Date: 2026-07-28 10:54:05 Functions: 100.0 % 48 48

            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 "config/config_info_operator.h"
      12              : 
      13              : #include <set>
      14              : #include <securec.h>
      15              : #include <sstream>
      16              : 
      17              : #include "hccl/hccl_ex.h"
      18              : #include "hccl/comm_channel_manager.h"
      19              : #include "common/type_def.h"
      20              : #include "queue_schedule/dgw_client.h"
      21              : #include "common/bqs_log.h"
      22              : #include "queue_manager.h"
      23              : #include "profile_manager.h"
      24              : #include "statistic_manager.h"
      25              : #include "subscribe_manager.h"
      26              : #include "schedule_config.h"
      27              : #include "dynamic_sched_mgr.hpp"
      28              : #include "queue_schedule_hal_interface_ref.h"
      29              : 
      30              : namespace bqs {
      31              : namespace {
      32              : // allowed max routes number
      33              : constexpr size_t MAX_ROUTES_NUM = 8000UL;
      34              : // allowed max endpoints number in one group
      35              : constexpr uint32_t MAX_ENDPOINTS_NUM_IN_SINGLE_GROUP = 1000U;
      36              : // max tag depth: hccl tag depth is 1024, so here is 1024/2
      37              : constexpr uint32_t MAX_TAG_DEPTH = 512U;
      38              : constexpr uint64_t INITIAL_MEMORY_SIZE = 5UL * 1024UL * 1024UL * 1024UL;  // 5G
      39              : constexpr uint16_t RESOURCE_ID_HOST_DEVICE_BIT_NUM = 14;
      40              : constexpr uint16_t RESOURCE_ID_ENABLE_BIT_MASK = 0x8000;
      41              : constexpr uint16_t ROUCE_ID_DEVICE_ID_DATA_MASK = 0x3FFF;
      42              : const std::unordered_set<int32_t> CMD_PROCESSED_BY_ALL_RES = {
      43              :     static_cast<int32_t>(ConfigCmd::DGW_CFG_CMD_BIND_ROUTE),
      44              :     static_cast<int32_t>(ConfigCmd::DGW_CFG_CMD_UNBIND_ROUTE),
      45              :     static_cast<int32_t>(ConfigCmd::DGW_CFG_CMD_STOP_SCHEDULE),
      46              :     static_cast<int32_t>(ConfigCmd::DGW_CFG_CMD_CLEAR_AND_RESTART_SCHEDULE)};
      47              : }
      48              : 
      49           38 : ConfigInfoOperator::ConfigInfoOperator(const uint32_t deviceId, const std::string groupNames)
      50           38 :     : deviceId_(deviceId), groupNames_(groupNames), clientVersion_(0U)
      51           38 : {}
      52              : 
      53           88 : BqsStatus ConfigInfoOperator::ParseConfigEvent(const uint32_t subEventId, const uint32_t queueId, void *mbuf,
      54              :     const uint16_t clientVersion)
      55              : {
      56           88 :     clientVersion_ = clientVersion;
      57              :     // get data buffer from mbuf
      58           88 :     void *mbufData = nullptr;
      59           88 :     auto getBuffRet = halMbufGetBuffAddr(PtrToPtr<void, Mbuf>(mbuf), &mbufData);
      60           88 :     if ((getBuffRet != static_cast<int32_t>(DRV_ERROR_NONE)) || (mbufData == nullptr)) {
      61            1 :         BQS_LOG_ERROR("halMbufGetBuffAddr from queue[%u] in device[%u] failed, error[%d]",
      62              :             queueId, deviceId_, getBuffRet);
      63            1 :         return BQS_STATUS_DRIVER_ERROR;
      64              :     }
      65              :     // get mbuf len
      66           87 :     uint64_t dataLen = 0UL;
      67           87 :     getBuffRet = halMbufGetDataLen(PtrToPtr<void, Mbuf>(mbuf), &dataLen);
      68           87 :     if (getBuffRet != static_cast<int32_t>(DRV_ERROR_NONE)) {
      69            1 :         BQS_LOG_ERROR("halMbufGetDataLen from queue[%u] in device[%u] failed, error[%d]",
      70              :             queueId, deviceId_, getBuffRet);
      71            1 :         return BQS_STATUS_DRIVER_ERROR;
      72              :     }
      73              : 
      74              :     // statistic info
      75           86 :     auto ret = BQS_STATUS_OK;
      76           86 :     const uintptr_t mbufDataAddr = PtrToValue(mbufData);
      77           86 :     const QueueSubEventType subEventType = static_cast<QueueSubEventType>(subEventId);
      78           86 :     switch (subEventType) {
      79           40 :         case QueueSubEventType::UPDATE_CONFIG: {
      80           40 :             ret = PreprocessUpdateCfgInfo(mbufDataAddr, static_cast<uint64_t>(dataLen));
      81           40 :             break;
      82              :         }
      83           23 :         case QueueSubEventType::QUERY_CONFIG_NUM: {
      84           23 :             ret = QueryConfigNum(mbufDataAddr, static_cast<uint64_t>(dataLen));
      85           23 :             break;
      86              :         }
      87            9 :         case QueueSubEventType::QUERY_CONFIG: {
      88            9 :             ret = QueryConfig(mbufDataAddr, static_cast<uint64_t>(dataLen));
      89            9 :             break;
      90              :         }
      91            7 :         case QueueSubEventType::DGW_CREATE_HCOM_HANDLE: {
      92            7 :             ret = CreateHcomHandle(mbufDataAddr, static_cast<uint64_t>(dataLen));
      93            7 :             break;
      94              :         }
      95            6 :         case QueueSubEventType::DGW_DESTORY_HCOM_HANDLE: {
      96            6 :             ret = DestroyHcomHandle(mbufDataAddr, static_cast<uint64_t>(dataLen));
      97            6 :             break;
      98              :         }
      99            1 :         default: {
     100            1 :             BQS_LOG_ERROR("Unsupport subEventId[%u] in bind relation procedure", subEventId);
     101            1 :             ret = BQS_STATUS_PARAM_INVALID;
     102            1 :             break;
     103              :         }
     104              :     }
     105           86 :     return ret;
     106              : }
     107              : 
     108           39 : BqsStatus ConfigInfoOperator::ProcessUpdateConfig(const uint32_t index)
     109              : {
     110           39 :     BQS_LOG_INFO("Update config[add/del group, bind/unbind route], stage [server:process]");
     111              :     // no need to check cfgInfo and updateCfgInfo_ nullptr
     112           39 :     ConfigInfo * const cfgInfo = updateCfgInfo_->cfgInfo;
     113           39 :     if ((CMD_PROCESSED_BY_ALL_RES.count(static_cast<int32_t>(cfgInfo->cmd)) == 0U) && (index != 0U)) {
     114            1 :         BQS_LOG_INFO("Thread[%u] need not process cmd[%d]", index, static_cast<int32_t>(cfgInfo->cmd));
     115            1 :         return BQS_STATUS_OK;
     116              :     }
     117              : 
     118           38 :     auto ret = BQS_STATUS_OK;
     119           38 :     switch (cfgInfo->cmd) {
     120           13 :         case ConfigCmd::DGW_CFG_CMD_BIND_ROUTE:
     121              :         case ConfigCmd::DGW_CFG_CMD_UNBIND_ROUTE: {
     122           13 :             ret = ProcessUpdateRoutes(index);
     123           13 :             break;
     124              :         }
     125            7 :         case ConfigCmd::DGW_CFG_CMD_ADD_GROUP: {
     126            7 :             ret = ProcessAddGroup();
     127            7 :             break;
     128              :         }
     129            8 :         case ConfigCmd::DGW_CFG_CMD_DEL_GROUP: {
     130            8 :             ret = ProcessDelGroup();
     131            8 :             break;
     132              :         }
     133            1 :         case ConfigCmd::DGW_CFG_CMD_UPDATE_PROFILING: {
     134            1 :             ret = ProcessUpdateProfiling();
     135            1 :             break;
     136              :         }
     137            2 :         case ConfigCmd::DGW_CFG_CMD_SET_HCCL_PROTOCOL: {
     138            2 :             ret = ProcessUpdateHcclProtocol();
     139            2 :             break;
     140              :         }
     141            4 :         case ConfigCmd::DGW_CFG_CMD_INIT_DYNAMIC_SCHEDULE: {
     142            4 :             ret = ProcessInitDynamicSched();
     143            4 :             break;
     144              :         }
     145            1 :         case ConfigCmd::DGW_CFG_CMD_STOP_SCHEDULE: {
     146            1 :             ret = ProcessStopSchedule(index);
     147            1 :             break;
     148              :         }
     149            1 :         case ConfigCmd::DGW_CFG_CMD_CLEAR_AND_RESTART_SCHEDULE: {
     150            1 :             ret = ProcessRestartSchedule(index);
     151            1 :             break;
     152              :         }
     153            1 :         default: {
     154            1 :             ret = BQS_STATUS_PARAM_INVALID;
     155            1 :             BQS_LOG_WARN("cmd[%d] is invalid.", static_cast<int32_t>(cfgInfo->cmd));
     156            1 :             break;
     157              :         }
     158              :     }
     159           38 :     return ret;
     160              : }
     161              : 
     162            9 : BqsStatus ConfigInfoOperator::QueryConfig(const uintptr_t mbufData, const uint64_t dataLen) const
     163              : {
     164            9 :     ConfigQuery * const cfgQry = PtrToPtr<void, ConfigQuery>(ValueToPtr(mbufData));
     165            9 :     if (cfgQry->mode == QueryMode::DGW_QUERY_MODE_GROUP) {
     166            3 :         return QueryGroup(mbufData, dataLen, false);
     167              :     }
     168            6 :     return QueryRoutes(mbufData, dataLen, false);
     169              : }
     170              : 
     171           23 : BqsStatus ConfigInfoOperator::QueryConfigNum(const uintptr_t mbufData, const uint64_t dataLen) const
     172              : {
     173           23 :     ConfigQuery * const cfgQry = PtrToPtr<void, ConfigQuery>(ValueToPtr(mbufData));
     174           23 :     if (cfgQry->mode == QueryMode::DGW_QUERY_MODE_GROUP) {
     175            8 :         return QueryGroup(mbufData, dataLen, true);
     176              :     }
     177           15 :     return QueryRoutes(mbufData, dataLen, true);
     178              : }
     179              : 
     180            7 : void ConfigInfoOperator::SplitStringWithDelimeter(const std::string rawStr, const char_t delimeter,
     181              :                                                   std::vector<std::string> &results) const
     182              : {
     183            7 :     if (rawStr.empty()) {
     184            1 :         BQS_LOG_INFO("str to split is empty");
     185            1 :         return;
     186              :     }
     187            6 :     std::stringstream strStream(rawStr);
     188            6 :     std::string strElement;
     189           18 :     while (getline(strStream, strElement, delimeter)) {
     190           12 :         results.emplace_back(strElement);
     191              :     }
     192            6 : }
     193              : 
     194           11 : BqsStatus ConfigInfoOperator::QueryGroupAllocInfo()
     195              : {
     196           11 :     if (!grpAllocInfos_.empty()) {
     197            1 :         BQS_LOG_INFO("grpAllocInfos_ has been inited");
     198            1 :         return BQS_STATUS_OK;
     199              :     }
     200           10 :     std::vector<std::string> groupNames;
     201           10 :     if (groupNames_.empty()) {
     202            4 :         const auto ret = QureySelfMemGroup(groupNames);
     203            4 :         if (ret != BQS_STATUS_OK) {
     204            0 :             return ret;
     205              :         }
     206              :     } else {
     207            6 :         SplitStringWithDelimeter(groupNames_, ',', groupNames);
     208              :     }
     209           18 :     for (const auto &groupName: groupNames) {
     210           10 :         GrpQueryGroupAddrPara queryPara = {};
     211           10 :         const errno_t eRet = memcpy_s(queryPara.grpName, BUFF_GRP_NAME_LEN,
     212           10 :             PtrToPtr<const char, const void>(groupName.c_str()) , strlen(groupName.c_str()) + 1);
     213           10 :         if (eRet != EOK) {
     214            1 :             BQS_LOG_ERROR("Failed to memcpy, ret[%d].", eRet);
     215            1 :             grpAllocInfos_.clear();
     216            2 :             return BQS_STATUS_INNER_ERROR;
     217              :         }
     218            9 :         queryPara.devId = deviceId_;
     219              : 
     220            9 :         GrpQueryGroupAddrInfo queryResults[BUFF_GROUP_ADDR_MAX_NUM] = {};
     221            9 :         uint32_t resultSize = 0U;
     222            9 :         const auto drvRet = halGrpQuery(GRP_QUERY_GROUP_ADDR_INFO, &queryPara,
     223              :             static_cast<uint32_t>(sizeof(queryPara)), &queryResults[0U], &resultSize);
     224            9 :         if ((drvRet != DRV_ERROR_NONE) || (static_cast<size_t>(resultSize) < sizeof(GrpQueryGroupAddrInfo))) {
     225            1 :             BQS_LOG_ERROR("Failed to halGrpQuery for group[%s], device[%u], ret[%d], resultSize[%u]",
     226              :                 queryPara.grpName, queryPara.devId, static_cast<int32_t>(drvRet), resultSize);
     227            1 :             grpAllocInfos_.clear();
     228            1 :             return BQS_STATUS_DRIVER_ERROR;
     229              :         }
     230              : 
     231            8 :         const uint32_t resultLen = static_cast<uint32_t>(resultSize / sizeof(GrpQueryGroupAddrInfo));
     232           16 :         for (uint32_t index = 0U; index < resultLen; ++index) {
     233            8 :             grpAllocInfos_.emplace_back(queryResults[static_cast<size_t>(index)]);
     234              :         }
     235              :     }
     236            8 :     return BQS_STATUS_OK;
     237           10 : }
     238              : 
     239            7 : BqsStatus ConfigInfoOperator::QureySelfMemGroup(std::vector<std::string> &groupNames) const
     240              : {
     241            7 :     std::unique_ptr<GroupQueryOutput> groupInfoPtr(new (std::nothrow) GroupQueryOutput());
     242            7 :     if (groupInfoPtr == nullptr) {
     243            0 :         BQS_LOG_ERROR("Fail to allocate GroupQueryOutput");
     244            0 :         return BQS_STATUS_INNER_ERROR;
     245              :     }
     246            7 :     GroupQueryOutput &groupInfo = *(groupInfoPtr.get());
     247            7 :     uint32_t groupInfoLen = 0U;
     248            7 :     pid_t curPid = drvDeviceGetBareTgid();
     249              :     // query group info for current qs process
     250            7 :     auto drvRet = halGrpQuery(GRP_QUERY_GROUPS_OF_PROCESS, &curPid, static_cast<uint32_t>(sizeof(curPid)),
     251              :         PtrToPtr<GroupQueryOutput, void>(&groupInfo), &groupInfoLen);
     252            7 :     if (drvRet != static_cast<int32_t>(DRV_ERROR_NONE)) {
     253            1 :         BQS_LOG_ERROR("halGrpQuery of qs[%d] failed, ret[%d]", curPid, drvRet);
     254            1 :         return BQS_STATUS_DRIVER_ERROR;
     255              :     }
     256              :     // not in any group, cannot do attach process
     257            6 :     if (groupInfoLen == 0U) {
     258            4 :         BQS_LOG_WARN("QS has not been added to any memory group!");
     259            4 :         return BQS_STATUS_OK;
     260              :     }
     261            2 :     if ((groupInfoLen % sizeof(groupInfo.grpQueryGroupsOfProcInfo[0])) != 0U) {
     262            1 :         BQS_LOG_ERROR("Group info size[%d] is invalid", groupInfoLen);
     263            1 :         return BQS_STATUS_DRIVER_ERROR;
     264              :     }
     265            1 :     const uint32_t groupNum = static_cast<uint32_t>(groupInfoLen / sizeof(groupInfo.grpQueryGroupsOfProcInfo[0]));
     266         1025 :     for (uint32_t i = 0U; i < groupNum; ++i) {
     267         1024 :         std::string grpName(groupInfo.grpQueryGroupsOfProcInfo[i].groupName);
     268         1024 :         if (!IsSvmShareGrp(grpName)) {
     269         1024 :             groupNames.emplace_back(grpName);
     270              :         }
     271         1024 :     }
     272            1 :     return BQS_STATUS_OK;
     273            7 : }
     274              : 
     275         1024 : bool ConfigInfoOperator::IsSvmShareGrp(const std::string &grpName) const
     276              : {
     277         1024 :     return grpName.find("svm_share_grp") != std::string::npos;
     278              : }
     279              : 
     280            8 : BqsStatus ConfigInfoOperator::CreateHcomHandle(const uintptr_t mbufData, const uint64_t dataLen)
     281              : {
     282            8 :     const auto queryGroupRet = QueryGroupAllocInfo();
     283            8 :     if (queryGroupRet != BQS_STATUS_OK) {
     284            0 :         return queryGroupRet;
     285              :     }
     286            8 :     HcomHandleInfo * const info = PtrToPtr<void, HcomHandleInfo>(ValueToPtr(mbufData));
     287            8 :     if (info->rankTableLen == 0UL) {
     288            0 :         BQS_LOG_ERROR("Invalid rank table len[%lu].", info->rankTableLen);
     289            0 :         return BQS_STATUS_PARAM_INVALID;
     290              :     }
     291              : 
     292            8 :     uint32_t tempAddHcomTab = 0U;
     293            8 :     bool isOverflow = false;
     294            8 :     BqsCheckAssign32UAdd(static_cast<uint32_t>(sizeof(HcomHandleInfo)), info->rankTableLen, tempAddHcomTab, isOverflow);
     295            8 :     if (isOverflow) {
     296            1 :         BQS_LOG_ERROR("tempAddHcomTab[%u] is invalid.", tempAddHcomTab);
     297            1 :         return BQS_STATUS_PARAM_INVALID;
     298              :     }
     299              : 
     300            7 :     uint32_t cfgLen = 0U;
     301            7 :     BqsCheckAssign32UAdd(tempAddHcomTab, static_cast<uint32_t>(sizeof(CfgRetInfo)), cfgLen, isOverflow);
     302            7 :     if (isOverflow) {
     303            0 :         BQS_LOG_ERROR("cfgLen[%u] is invalid.", cfgLen);
     304            0 :         return BQS_STATUS_PARAM_INVALID;
     305              :     }
     306              : 
     307              :     // check dataLen
     308            7 :     if (dataLen < cfgLen) {
     309            0 :         BQS_LOG_ERROR("dataLen[%lu] is invalid, cfgLen is [%u].", dataLen, cfgLen);
     310            0 :         return BQS_STATUS_PARAM_INVALID;
     311              :     }
     312              : 
     313              :     // get rank table
     314            7 :     char_t * const rankTablePtr = PtrToPtr<void, char>(ValueToPtr(mbufData + sizeof(HcomHandleInfo)));
     315            7 :     const std::string rankTable(rankTablePtr, info->rankTableLen);
     316              : 
     317            7 :     auto result = BQS_STATUS_OK;
     318              :     // create hcom handle
     319            7 :     CommAttr attr = {};
     320            7 :     attr.deviceId = deviceId_;
     321            7 :     HcclComm hcomHandle = nullptr;
     322            7 :     const HcclResult hcclRet = HcclInitComm(rankTable.c_str(), static_cast<uint32_t>(info->rankId), &attr, &hcomHandle);
     323            7 :     if (hcclRet != HCCL_SUCCESS) {
     324            0 :         result = BQS_STATUS_HCCL_ERROR;
     325            0 :         BQS_LOG_ERROR("Failed to create hcom handle, hccl ret is[%d].", static_cast<int32_t>(hcclRet));
     326              :     } else {
     327           13 :         for (const auto &grpAllocInfo: grpAllocInfos_) {
     328            7 :             const uint64_t memorySize = (bqs::RunContext::HOST != bqs::GetRunContext()) ?
     329            7 :                 static_cast<uint64_t>(grpAllocInfo.size) : INITIAL_MEMORY_SIZE;
     330            7 :             const auto registerRet = HcclRegisterMemory(hcomHandle,
     331            7 :                 ValueToPtr(static_cast<uint64_t>(grpAllocInfo.addr)), memorySize);
     332            7 :             if (registerRet != HCCL_SUCCESS) {
     333            1 :                 result = BQS_STATUS_HCCL_ERROR;
     334            1 :                 BQS_LOG_ERROR("Failed to register memory, hccl ret is[%d].", static_cast<int32_t>(registerRet));
     335            1 :                 HcclFinalizeComm(hcomHandle);
     336            1 :                 break;
     337              :             }
     338            6 :             BQS_LOG_INFO("Register meomory size[%lu]", memorySize);
     339              :         }
     340            7 :         if (result == BQS_STATUS_OK) {
     341            6 :             info->hcomHandle = PtrToValue(hcomHandle);
     342            6 :             BQS_LOG_INFO("Success to create hcom handle[%lu]", info->hcomHandle);
     343              :         }
     344              :     }
     345              : 
     346              :     // write result to mbuf
     347            7 :     CfgRetInfo * const retInfo = PtrToPtr<void, CfgRetInfo>(
     348            7 :         ValueToPtr(mbufData + sizeof(HcomHandleInfo) + info->rankTableLen));
     349            7 :     retInfo->retCode = static_cast<int32_t>(result);
     350              : 
     351            7 :     return BQS_STATUS_OK;
     352            7 : }
     353              : 
     354            7 : BqsStatus ConfigInfoOperator::DestroyHcomHandle(const uintptr_t mbufData, const uint64_t dataLen) const
     355              : {
     356            7 :     HcomHandleInfo * const info = PtrToPtr<void, HcomHandleInfo>(ValueToPtr(mbufData));
     357              :     // check dataLen
     358            7 :     bool overFlow = false;
     359            7 :     uint64_t cfgLen = BqsCheckAssign64UAdd(static_cast<uint64_t>(sizeof(HcomHandleInfo) + sizeof(CfgRetInfo)),
     360              :         info->rankTableLen, overFlow);
     361            7 :     if (overFlow || (dataLen < cfgLen)) {
     362            1 :         BQS_LOG_ERROR("dataLen[%lu] is invalid, cfgLen is [%lu].", dataLen, cfgLen);
     363            1 :         return BQS_STATUS_PARAM_INVALID;
     364              :     }
     365              : 
     366              :     // get hcom handle from mbuf
     367            6 :     const HcclComm hcomHandle = ValueToPtr(info->hcomHandle);
     368            6 :     if (hcomHandle == nullptr) {
     369            0 :         BQS_LOG_ERROR("Hcom handle is nullptr.");
     370            0 :         return BQS_STATUS_PARAM_INVALID;
     371              :     }
     372            6 :     BQS_LOG_RUN_INFO("Begin to Destroy hcom handle[%lu].", info->hcomHandle);
     373           12 :     for (const auto &grpAllocInfo: grpAllocInfos_) {
     374            6 :         const auto unRegisterRet = HcclUnregisterMemory(hcomHandle,
     375            6 :             ValueToPtr(static_cast<uint64_t>(grpAllocInfo.addr)));
     376            6 :         if (unRegisterRet != HCCL_SUCCESS) {
     377            4 :             BQS_LOG_ERROR("Failed to unRegister memory, hccl ret is[%d].", static_cast<int32_t>(unRegisterRet));
     378              :         }
     379              :     }
     380            6 :     BQS_LOG_RUN_INFO("After HcclUnregisterMemory when Destroy hcom handle[%lu].", info->hcomHandle);
     381              : 
     382              :     // destroy hcom handle
     383            6 :     auto result = BQS_STATUS_OK;
     384            6 :     const HcclResult hcclRet = HcclFinalizeComm(hcomHandle);
     385            6 :     if (hcclRet != HCCL_SUCCESS) {
     386            0 :         result = BQS_STATUS_HCCL_ERROR;
     387            0 :         BQS_LOG_ERROR("Failed to destroy hcom handle, hccl ret is[%d].", static_cast<int32_t>(hcclRet));
     388              :     } else {
     389            6 :         BQS_LOG_INFO("Success to destroy hcom handle[%lu]", info->hcomHandle);
     390              :     }
     391            6 :     BQS_LOG_RUN_INFO("After HcclFinalizeComm when Destroy hcom handle[%lu].", info->hcomHandle);
     392              : 
     393              :     // write result to mbuf
     394            6 :     CfgRetInfo * const retInfo = PtrToPtr<void, CfgRetInfo>(
     395            6 :         ValueToPtr(mbufData + sizeof(HcomHandleInfo) + info->rankTableLen));
     396            6 :     retInfo->retCode = static_cast<int32_t>(result);
     397              : 
     398            6 :     bqs::StatisticManager::GetInstance().ResetStatistic();
     399            6 :     bqs::ProfileManager::GetInstance(0U).ResetProfiling();
     400            6 :     if (GlobalCfg::GetInstance().GetNumaFlag()) {
     401            0 :         bqs::ProfileManager::GetInstance(1U).ResetProfiling();
     402              :     }
     403            6 :     return BQS_STATUS_OK;
     404              : }
     405              : 
     406           13 : BqsStatus ConfigInfoOperator::QueryGroup(const uintptr_t mbufData, const uint64_t dataLen, const bool onlyQryNum) const
     407              : {
     408           13 :     if (dataLen < sizeof(ConfigQuery)) {
     409            1 :         BQS_LOG_ERROR("dataLen[%lu] is invalid.", dataLen);
     410            1 :         return BQS_STATUS_PARAM_INVALID;
     411              :     }
     412              :     // no need check cfgQry nullptr
     413           12 :     ConfigQuery * const cfgQry = PtrToPtr<void, ConfigQuery>(ValueToPtr(mbufData));
     414           12 :     const uint32_t groupId = static_cast<uint32_t>(cfgQry->qry.groupQry.groupId);
     415           12 :     auto &entitiesInGroup = BindRelation::GetInstance().GetEntitiesInGroup(groupId);
     416              : 
     417           12 :     const size_t endpointNum = onlyQryNum ? 0UL : cfgQry->qry.routeQry.routeNum;
     418              :     // check total len
     419           12 :     const size_t totalLen = onlyQryNum ? (sizeof(ConfigQuery) + sizeof(CfgRetInfo)) :
     420            3 :         (sizeof(ConfigQuery) + sizeof(ConfigInfo) + (endpointNum * sizeof(Endpoint)) + sizeof(CfgRetInfo));
     421           12 :     if (dataLen != totalLen) {
     422            1 :         BQS_LOG_ERROR("mbuf dataLen[%lu] is not equal with totalLen[%zu].", dataLen, totalLen);
     423            1 :         return BQS_STATUS_PARAM_INVALID;
     424              :     }
     425              : 
     426           11 :     if (onlyQryNum) {
     427            8 :         cfgQry->qry.groupQry.endpointNum = static_cast<uint32_t>(entitiesInGroup.size());
     428            8 :         CfgRetInfo * const retInfo = PtrToPtr<void, CfgRetInfo>(ValueToPtr(mbufData + sizeof(ConfigQuery)));
     429            8 :         retInfo->retCode = (cfgQry->qry.groupQry.endpointNum == 0U) ?
     430              :             static_cast<int32_t>(BQS_STATUS_GROUP_NOT_EXIST) : static_cast<int32_t>(BQS_STATUS_OK);
     431            8 :         BQS_LOG_INFO("endpointNum is %u in group[%u].", cfgQry->qry.groupQry.endpointNum, groupId);
     432            8 :         return BQS_STATUS_OK;
     433              :     }
     434              : 
     435              :     // check number
     436            3 :     const uintptr_t results = mbufData + (totalLen - sizeof(CfgRetInfo));
     437            3 :     CfgRetInfo * const retInfo = PtrToPtr<void, CfgRetInfo>(ValueToPtr(results));
     438            3 :     if (endpointNum != entitiesInGroup.size()) {
     439            0 :         retInfo->retCode = static_cast<int32_t>(BQS_STATUS_PARAM_INVALID);
     440            0 :         BQS_LOG_ERROR("endpoint num in group[%u] info is [%zu], but searched endpoint num is [%zu].",
     441              :             groupId, endpointNum, entitiesInGroup.size());
     442            0 :         return BQS_STATUS_PARAM_INVALID;
     443              :     }
     444              : 
     445            3 :     BQS_LOG_INFO("Group [get], stage [server:process], relation [size:%zu]", entitiesInGroup.size());
     446              :     // convert and record route
     447              :     Endpoint * const endpoints =
     448            3 :         PtrToPtr<void, Endpoint>(ValueToPtr(mbufData + sizeof(ConfigQuery) + sizeof(ConfigInfo)));
     449            3 :     size_t idx = 0UL;
     450           10 :     for (auto &entity : entitiesInGroup) {
     451            7 :         Endpoint * const endpoint = PtrAdd<Endpoint>(endpoints, endpointNum, idx);
     452            7 :         (void)ConvertToEndpoint(*entity, *endpoint);
     453            7 :         idx++;
     454              :     }
     455            3 :     retInfo->retCode = static_cast<int32_t>(BQS_STATUS_OK);
     456            3 :     return BQS_STATUS_OK;
     457              : }
     458              : 
     459           23 : BqsStatus ConfigInfoOperator::QueryRoutes(const uintptr_t mbufData, const uint64_t dataLen, const bool onlyQryNum) const
     460              : {
     461              :     // check data len
     462           23 :     if (dataLen < sizeof(ConfigQuery)) {
     463            0 :         BQS_LOG_ERROR("dataLen[%lu] is invalid.", dataLen);
     464            0 :         return BQS_STATUS_PARAM_INVALID;
     465              :     }
     466              :     // no need check cfgQry nullptr
     467           23 :     ConfigQuery * const cfgQry = PtrToPtr<void, ConfigQuery>(ValueToPtr(mbufData));
     468              : 
     469           23 :     const size_t routeNum = onlyQryNum ? 0UL : cfgQry->qry.routeQry.routeNum;
     470              :     // check total len
     471           23 :     const size_t totalLen = onlyQryNum ? (sizeof(ConfigQuery) + sizeof(CfgRetInfo)) :
     472            6 :         (sizeof(ConfigQuery) + sizeof(ConfigInfo) + (routeNum * sizeof(Route)) + sizeof(CfgRetInfo));
     473           23 :     if (dataLen != totalLen) {
     474            1 :         BQS_LOG_ERROR("mbuf dataLen[%lu] is not equal with totalLen[%zu].", dataLen, totalLen);
     475            1 :         return BQS_STATUS_PARAM_INVALID;
     476              :     }
     477              : 
     478           22 :     auto ret = BQS_STATUS_OK;
     479           22 :     switch (cfgQry->mode) {
     480            4 :         case QueryMode::DGW_QUERY_MODE_SRC_ROUTE: {
     481            4 :             const EntityInfoPtr src = CreateEntityInfo(cfgQry->qry.routeQry.src, true);
     482            4 :             ret = (src == nullptr) ? BQS_STATUS_FAILED : QueryRoutesBySrc(mbufData, *src, onlyQryNum);
     483            4 :             break;
     484            4 :         }
     485            5 :         case QueryMode::DGW_QUERY_MODE_DST_ROUTE: {
     486            5 :             const EntityInfoPtr dst = CreateEntityInfo(cfgQry->qry.routeQry.dst, true);
     487            5 :             ret = (dst == nullptr) ? BQS_STATUS_FAILED : QueryRoutesByDst(mbufData, *dst, onlyQryNum);
     488            5 :             break;
     489            5 :         }
     490            8 :         case QueryMode::DGW_QUERY_MODE_ALL_ROUTE: {
     491            8 :             ret = QueryAllRoutes(mbufData, onlyQryNum);
     492            8 :             break;
     493              :         }
     494            4 :         case QueryMode::DGW_QUERY_MODE_SRC_DST_ROUTE: {
     495            4 :             const EntityInfoPtr src = CreateEntityInfo(cfgQry->qry.routeQry.src, true);
     496            4 :             const EntityInfoPtr dst = CreateEntityInfo(cfgQry->qry.routeQry.dst, true);
     497            4 :             ret = ((src == nullptr) || (dst == nullptr)) ? BQS_STATUS_FAILED :
     498            4 :                 QueryRoutesBySrcAndDst(mbufData, *src, *dst, onlyQryNum);
     499            4 :             break;
     500            4 :         }
     501            1 :         default: {
     502            1 :             ret = BQS_STATUS_PARAM_INVALID;
     503            1 :             BQS_LOG_ERROR("Unsupported query type{0:src, 1:dst, 2:src-and-dst 3:all}:%d",
     504              :                 static_cast<int32_t>(cfgQry->mode));
     505            1 :             break;
     506              :         }
     507              :     }
     508           22 :     return ret;
     509              : }
     510              : 
     511            4 : BqsStatus ConfigInfoOperator::QueryRoutesBySrc(const uintptr_t mbufData, const EntityInfo &src,
     512              :                                                const bool onlyQryNum) const
     513              : {
     514            4 :     std::list<std::pair<const EntityInfo *, const EntityInfo *>> routeList;
     515              : 
     516            4 :     QueryRoutesBySrcFromRelation(src, BindRelation::GetInstance().GetSrcToDstRelation(), routeList);
     517            4 :     if (GlobalCfg::GetInstance().GetNumaFlag()) {
     518            4 :         QueryRoutesBySrcFromRelation(src, BindRelation::GetInstance().GetSrcToDstExtraRelation(), routeList);
     519              :     }
     520              : 
     521            8 :     return SaveQueryResult(routeList, mbufData, onlyQryNum);
     522            4 : }
     523              : 
     524            8 : void ConfigInfoOperator::QueryRoutesBySrcFromRelation(const EntityInfo &src,
     525              :     const MapEnitityInfoToInfoSet &srcToDstRelation,
     526              :     std::list<std::pair<const EntityInfo*, const EntityInfo*>> &routeList) const
     527              : {
     528            8 :     const auto iter = srcToDstRelation.find(src);
     529            8 :     if (iter == srcToDstRelation.end()) {
     530            5 :         BQS_LOG_WARN("Record does not exist according to src Id:[%u] type:[%d]", src.GetId(),
     531              :                      static_cast<int32_t>(src.GetType()));
     532              :     } else {
     533              :         // generate route list
     534            3 :         const auto &dstSet = iter->second;
     535            8 :         for (auto dstIter = dstSet.begin(); dstIter != dstSet.end(); ++dstIter) {
     536            5 :             routeList.emplace_back(std::make_pair(&src, &(*dstIter)));
     537              :         }
     538              :     }
     539            8 : }
     540              : 
     541            5 : BqsStatus ConfigInfoOperator::QueryRoutesByDst(const uintptr_t mbufData, const EntityInfo &dst,
     542              :                                                const bool onlyQryNum) const
     543              : {
     544            5 :     std::list<std::pair<const EntityInfo *, const EntityInfo *>> routeList;
     545              : 
     546            5 :     QueryRoutesByDstFromRelation(dst, BindRelation::GetInstance().GetDstToSrcRelation(), routeList);
     547            5 :     if (GlobalCfg::GetInstance().GetNumaFlag()) {
     548            5 :         QueryRoutesByDstFromRelation(dst, BindRelation::GetInstance().GetDstToSrcExtraRelation(), routeList);
     549              :     }
     550              : 
     551           10 :     return SaveQueryResult(routeList, mbufData, onlyQryNum);
     552            5 : }
     553              : 
     554           10 : void ConfigInfoOperator::QueryRoutesByDstFromRelation(const EntityInfo &dst,
     555              :     const MapEnitityInfoToInfoSet &dstToSrcRelation,
     556              :     std::list<std::pair<const EntityInfo*, const EntityInfo*>> &routeList) const
     557              : {
     558           10 :     const auto iter = dstToSrcRelation.find(dst);
     559           10 :     if (iter == dstToSrcRelation.end()) {
     560            7 :         BQS_LOG_WARN("Record does not exist according to dst Id:[%u] type:[%d]", dst.GetId(),
     561              :                      static_cast<int32_t>(dst.GetType()));
     562              :     } else {
     563            3 :         const auto &srcSet = iter->second;
     564              :         // generate route list
     565            6 :         for (auto srcIter = srcSet.begin(); srcIter != srcSet.end(); ++srcIter) {
     566            3 :             routeList.emplace_back(std::make_pair(&(*srcIter), &dst));
     567              :         }
     568              :     }
     569           10 : }
     570              : 
     571            4 : BqsStatus ConfigInfoOperator::QueryRoutesBySrcAndDst(const uintptr_t mbufData, const EntityInfo &src,
     572              :                                                      const EntityInfo &dst, const bool onlyQryNum) const
     573              : {
     574            4 :     uint32_t searchedRouteNum = 0U;
     575            4 :     auto &srcToDstRelation = BindRelation::GetInstance().GetSrcToDstRelation();
     576            4 :     const auto iter = srcToDstRelation.find(src);
     577            4 :     if ((iter != srcToDstRelation.end()) && (iter->second.count(dst) != 0UL)) {
     578            3 :         searchedRouteNum = 1U;
     579              :     } else {
     580            1 :         if (GlobalCfg::GetInstance().GetNumaFlag()) {
     581            1 :             const auto &srcToDstRelationTmp = BindRelation::GetInstance().GetSrcToDstExtraRelation();
     582            1 :             const auto it = srcToDstRelationTmp.find(src);
     583            1 :             if ((it != srcToDstRelationTmp.end()) && (it->second.count(dst) != 0UL)) {
     584            0 :                 searchedRouteNum = 1U;
     585              :             }
     586              :         }
     587              :     }
     588              : 
     589              :     // generate route list
     590            4 :     std::list<std::pair<const EntityInfo *, const EntityInfo *>> routeList;
     591            4 :     if (searchedRouteNum != 0U) {
     592            3 :         routeList.emplace_back(std::make_pair(&src, &dst));
     593              :     } else {
     594            1 :         BQS_LOG_WARN("Record does not exist according to src Id:[%u] type:[%d]", src.GetId(),
     595              :                      static_cast<int32_t>(src.GetType()));
     596              :     }
     597            8 :     return SaveQueryResult(routeList, mbufData, onlyQryNum);
     598            4 : }
     599              : 
     600            8 : BqsStatus ConfigInfoOperator::QueryAllRoutes(const uintptr_t mbufData, const bool onlyQryNum) const
     601              : {
     602              :     // gennerate route list
     603            8 :     std::list<std::pair<const EntityInfo *, const EntityInfo *>> routeList;
     604            8 :     auto &srcToDstRelation = BindRelation::GetInstance().GetSrcToDstRelation();
     605           23 :     for (auto iter = srcToDstRelation.begin(); iter != srcToDstRelation.end(); ++iter) {
     606           15 :         const auto &dstSet = iter->second;
     607           33 :         for (auto &dst : dstSet) {
     608           18 :             routeList.emplace_back(std::make_pair(&(iter->first), &dst));
     609              :         }
     610              :     }
     611              : 
     612            8 :     if (GlobalCfg::GetInstance().GetNumaFlag()) {
     613            4 :         const auto &srcToDstRelationTmp = BindRelation::GetInstance().GetSrcToDstExtraRelation();
     614            4 :         for (auto iter = srcToDstRelationTmp.begin(); iter != srcToDstRelationTmp.end(); ++iter) {
     615            0 :             const auto &dstSet = iter->second;
     616            0 :             for (auto &dst : dstSet) {
     617            0 :                 routeList.emplace_back(std::make_pair(&(iter->first), &dst));
     618              :             }
     619              :         }
     620              :     }
     621              : 
     622           16 :     return SaveQueryResult(routeList, mbufData, onlyQryNum);
     623            8 : }
     624              : 
     625           22 : BqsStatus ConfigInfoOperator::SaveQueryResult(std::list<std::pair<const EntityInfo *, const EntityInfo *>> &routeList,
     626              :                                               const uintptr_t mbufData, const bool onlyQryNum) const
     627              : {
     628              :     // no need check cfgQry nullptr
     629           22 :     ConfigQuery * const cfgQry = PtrToPtr<void, ConfigQuery>(ValueToPtr(mbufData));
     630           22 :     const size_t totalRouteNum = routeList.size();
     631           22 :     if (onlyQryNum) {
     632           15 :         cfgQry->qry.routeQry.routeNum = static_cast<uint32_t>(totalRouteNum);
     633           15 :         CfgRetInfo * const retInfo = PtrToPtr<void, CfgRetInfo>(ValueToPtr(mbufData + sizeof(ConfigQuery)));
     634           15 :         retInfo->retCode = static_cast<int32_t>(BQS_STATUS_OK);
     635           15 :         return BQS_STATUS_OK;
     636              :     }
     637              : 
     638              :     // check number
     639            7 :     const size_t routeNum = static_cast<size_t>(cfgQry->qry.routeQry.routeNum);
     640            7 :     const uintptr_t results = mbufData + sizeof(ConfigQuery) + sizeof(ConfigInfo) + (routeNum * sizeof(Route));
     641            7 :     CfgRetInfo * const retInfo = PtrToPtr<void, CfgRetInfo>(ValueToPtr(results));
     642            7 :     if (routeNum != totalRouteNum) {
     643            1 :         retInfo->retCode = static_cast<int32_t>(BQS_STATUS_PARAM_INVALID);
     644            1 :         BQS_LOG_ERROR("Route num in query info is [%lu], but searched route num is [%lu].", routeNum, totalRouteNum);
     645            1 :         return BQS_STATUS_PARAM_INVALID;
     646              :     }
     647              : 
     648              :     // convert and record route
     649            6 :     Route * const routes = PtrToPtr<void, Route>(ValueToPtr(mbufData + sizeof(ConfigQuery) + sizeof(ConfigInfo)));
     650            6 :     size_t idx = 0UL;
     651           17 :     for (auto iter = routeList.begin(); iter != routeList.end(); ++iter) {
     652           11 :         Route * const route = PtrAdd<Route>(routes, routeNum, idx);
     653           11 :         (void)ConvertToRoute(*(iter->first), *(iter->second), *route);
     654           11 :         idx++;
     655              :     }
     656            6 :     retInfo->retCode = static_cast<int32_t>(BQS_STATUS_OK);
     657            6 :     return BQS_STATUS_OK;
     658              : }
     659              : 
     660           11 : BqsStatus ConfigInfoOperator::ConvertToRoute(const EntityInfo &src, const EntityInfo &dst, Route &route) const
     661              : {
     662           11 :     route.status = RouteStatus::ACTIVE;
     663           11 :     (void)ConvertToEndpoint(src, route.src);
     664           11 :     (void)ConvertToEndpoint(dst, route.dst);
     665           11 :     return BQS_STATUS_OK;
     666              : }
     667              : 
     668           32 : BqsStatus ConfigInfoOperator::ConvertToEndpoint(const EntityInfo &entity, Endpoint &endpoint) const
     669              : {
     670           32 :     auto ret = BQS_STATUS_OK;
     671           32 :     endpoint.status = EndpointStatus::AVAILABLE;
     672           32 :     switch (entity.GetType()) {
     673           25 :         case dgw::EntityType::ENTITY_QUEUE: {
     674           25 :             if (endpoint.type == EndpointType::MEM_QUEUE) {
     675            2 :                 endpoint.attr.memQueueAttr.queueId = static_cast<int32_t>(entity.GetId());
     676              :             } else {
     677           23 :                 endpoint.type = EndpointType::QUEUE;
     678           23 :                 endpoint.attr.queueAttr.queueId = static_cast<int32_t>(entity.GetId());
     679              :             }
     680           25 :             break;
     681              :         }
     682            3 :         case dgw::EntityType::ENTITY_GROUP: {
     683            3 :             endpoint.type = EndpointType::GROUP;
     684            3 :             endpoint.attr.groupAttr.groupId = static_cast<int32_t>(entity.GetId());
     685              :             // group policy && endpoint num
     686            3 :             break;
     687              :         }
     688            3 :         case dgw::EntityType::ENTITY_TAG: {
     689            3 :             endpoint.type = EndpointType::COMM_CHANNEL;
     690            3 :             CommChannelAttr &attr = endpoint.attr.channelAttr;
     691            3 :             const dgw::CommChannel * const channel = entity.GetCommChannel();
     692            3 :             if (channel != nullptr) {
     693            3 :                 attr.handle = PtrToValue(channel->GetHandle());
     694            3 :                 attr.localTagId = channel->GetLocalTagId();
     695            3 :                 attr.peerTagId = channel->GetPeerTagId();
     696            3 :                 attr.localRankId = channel->GetLocalRankId();
     697            3 :                 attr.peerRankId = channel->GetPeerRankId();
     698            3 :                 attr.localTagDepth = channel->GetLocalTagDepth();
     699            3 :                 attr.peerTagDepth = channel->GetPeerTagDepth();
     700              :             }
     701            3 :             break;
     702              :         }
     703            1 :         default: {
     704            1 :             BQS_LOG_ERROR("Unsupport entity type[%d].", static_cast<int32_t>(entity.GetType()));
     705            1 :             ret = BQS_STATUS_PARAM_INVALID;
     706            1 :             break;
     707              :         }
     708              :     }
     709           32 :     return ret;
     710              : }
     711              : 
     712           95 : EntityInfoPtr ConfigInfoOperator::CreateEntityInfo(const Endpoint &endpoint, const bool isQry) const
     713              : {
     714           95 :     uint32_t id = 0U;
     715           95 :     uint32_t localDeviceId = deviceId_;
     716           95 :     OptionalArg args = {};
     717           95 :     args.eType = dgw::EntityType::ENTITY_INVALID;
     718           95 :     args.schedCfgKey = endpoint.rootModelId;
     719           95 :     args.globalId = endpoint.globalId;
     720           95 :     args.uuId = endpoint.modelId;
     721              : 
     722           95 :     dgw::EntityType &eType = args.eType;
     723           95 :     bqs::GroupPolicy &policy = args.policy;
     724           95 :     const dgw::CommChannel* &channelPtr = args.channelPtr;
     725           95 :     auto ret = BQS_STATUS_OK;
     726           95 :     switch (endpoint.type) {
     727           76 :         case EndpointType::QUEUE: {
     728           76 :             eType = dgw::EntityType::ENTITY_QUEUE;
     729           76 :             id = static_cast<uint32_t>(endpoint.attr.queueAttr.queueId);
     730           76 :             break;
     731              :         }
     732            3 :         case EndpointType::MEM_QUEUE: {
     733            3 :             eType = dgw::EntityType::ENTITY_QUEUE;
     734            3 :             id = static_cast<uint32_t>(endpoint.attr.memQueueAttr.queueId);
     735            3 :             break;
     736              :         }
     737            8 :         case EndpointType::COMM_CHANNEL: {
     738            8 :             eType = dgw::EntityType::ENTITY_TAG;
     739            8 :             const CommChannelAttr &attr = endpoint.attr.channelAttr;
     740            8 :             ret = CheckCommChannelAttr(attr, isQry);
     741            8 :             if (ret == BQS_STATUS_OK) {
     742            5 :                 const dgw::CommChannel channel(ValueToPtr(attr.handle), attr.localTagId, attr.peerTagId,
     743            5 :                                                attr.localRankId, attr.peerRankId, attr.localTagDepth,
     744            5 :                                                attr.peerTagDepth);
     745            5 :                 id = dgw::CommChannelManager::GetInstance().GetCommChannelId(channel, channelPtr);
     746            5 :             }
     747            8 :             break;
     748              :         }
     749            7 :         case EndpointType::GROUP: {
     750            7 :             eType = dgw::EntityType::ENTITY_GROUP;
     751            7 :             id = static_cast<uint32_t>(endpoint.attr.groupAttr.groupId);
     752            7 :             policy = endpoint.attr.groupAttr.policy;
     753            7 :             break;
     754              :         }
     755            1 :         default: {
     756            1 :             ret = BQS_STATUS_PARAM_INVALID;
     757            1 :             BQS_LOG_DEBUG("Unsupport endpoint type[%d].", static_cast<int32_t>(endpoint.type));
     758            1 :             break;
     759              :         }
     760              :     }
     761           95 :     if (ret != BQS_STATUS_OK) {
     762            4 :         return nullptr;
     763              :     }
     764              : 
     765           91 :     if (clientVersion_ >= 2U) {
     766            0 :         args.peerInstanceNum = endpoint.peerNum;
     767            0 :         args.localInstanceIndex = endpoint.localId;
     768              :     }
     769              : 
     770           91 :     if (GlobalCfg::GetInstance().GetNumaFlag() && ((endpoint.resId & RESOURCE_ID_ENABLE_BIT_MASK) != 0U)) {
     771            4 :         localDeviceId = (endpoint.resId & ROUCE_ID_DEVICE_ID_DATA_MASK);
     772              :     }
     773              : 
     774           91 :     uint32_t &queueType = args.queueType;
     775           91 :     if (endpoint.type == EndpointType::MEM_QUEUE) {
     776              :         // parse hostQ and device belonged
     777            3 :         bool isHostQueue = (((endpoint.resId >> RESOURCE_ID_HOST_DEVICE_BIT_NUM) & 1) != 0) ? true : false;
     778            3 :         uint32_t onwerDeviceId = ((endpoint.resId & RESOURCE_ID_ENABLE_BIT_MASK) != 0U) ?
     779            2 :                                   (endpoint.resId & ROUCE_ID_DEVICE_ID_DATA_MASK) : deviceId_;
     780            3 :         localDeviceId = onwerDeviceId;
     781            3 :         queueType = endpoint.attr.memQueueAttr.queueType;
     782            3 :         if ((bqs::GetRunContext() != bqs::RunContext::HOST) && (&drvGetLocalDevIDByHostDevID != nullptr)) {
     783            1 :             auto retCode = drvGetLocalDevIDByHostDevID(onwerDeviceId, &localDeviceId);
     784            1 :             if (retCode != static_cast<int32_t>(DRV_ERROR_NONE)) {
     785            1 :                 BQS_LOG_INFO("host devid(%u) transform to local devid.", localDeviceId);
     786            1 :                 localDeviceId = onwerDeviceId;
     787              :             }
     788              :         }
     789            3 :         BQS_LOG_INFO("[CreateEntityInfo] qid=%u, endpoint.resId=%u, isHostQueue=%d, "
     790              :                      "onwerDeviceId=%u, localDeviceId=%u, queueType=%u",
     791              :                      id, endpoint.resId, isHostQueue, onwerDeviceId, localDeviceId, queueType);
     792              :     }
     793              : 
     794              :     // create entity info ptr
     795           91 :     EntityInfoPtr entityPtr = nullptr;
     796              :     try {
     797           91 :         entityPtr = std::make_shared<EntityInfo>(id, localDeviceId, &args);
     798            0 :     } catch (...) {
     799            0 :         BQS_LOG_ERROR("Create entity info ptr failed, id[%u], type[%d].",
     800              :             id, static_cast<int32_t>(eType));
     801            0 :     }
     802              : 
     803           91 :     BQS_LOG_INFO("Create entity success: %s", entityPtr->ToString().c_str());
     804           91 :     return entityPtr;
     805              : }
     806              : 
     807           15 : BqsStatus ConfigInfoOperator::AttachAndCheckQueue(const EntityInfo& src, const EntityInfo& dst) const
     808              : {
     809           15 :     auto srcRet = AttachQueue(src);
     810           15 :     auto dstRet = AttachQueue(dst);
     811           15 :     auto ret = (srcRet != BQS_STATUS_OK) ? srcRet : dstRet;
     812           15 :     if (ret != BQS_STATUS_OK) {
     813            1 :         BQS_LOG_ERROR("Fail to attach src[%s] or dst[%s], srcRet[%d], dstRet[%d].",
     814              :             src.ToString().c_str(), dst.ToString().c_str(), static_cast<int32_t>(srcRet), static_cast<int32_t>(dstRet));
     815            1 :         return ret;
     816              :     }
     817              : 
     818           14 :     srcRet = CheckQueueAuth(src, true);
     819           14 :     dstRet = CheckQueueAuth(dst, false);
     820           14 :     ret = (srcRet != BQS_STATUS_OK) ? srcRet : dstRet;
     821           14 :     if (ret != BQS_STATUS_OK) {
     822            0 :         BQS_LOG_ERROR("Fail to check src[%s] or dst[%s] queue auth, srcRet[%d], dstRet[%d].",
     823              :             src.ToString().c_str(), dst.ToString().c_str(), static_cast<int32_t>(srcRet), static_cast<int32_t>(dstRet));
     824            0 :         return ret;
     825              :     }
     826           14 :     return BQS_STATUS_OK;
     827              : }
     828              : 
     829           32 : BqsStatus ConfigInfoOperator::AttachQueue(const EntityInfo &info) const
     830              : {
     831           32 :     auto ret = BQS_STATUS_OK;
     832           32 :     switch (info.GetType()) {
     833            2 :         case dgw::EntityType::ENTITY_TAG: {
     834            2 :             break;
     835              :         }
     836           25 :         case dgw::EntityType::ENTITY_QUEUE: {
     837           25 :             const auto drvRet = halQueueAttach(info.GetDeviceId(), info.GetId(), 0);
     838           25 :             if (drvRet != DRV_ERROR_NONE) {
     839            3 :                 BQS_LOG_ERROR("Fail to attach queue[%s], device[%u], ret[%d]", info.ToString().c_str(),
     840              :                               info.GetDeviceId(), static_cast<int32_t>(drvRet));
     841            3 :                 ret = BQS_STATUS_DRIVER_ERROR;
     842              :             }
     843           25 :             break;
     844              :         }
     845            4 :         case dgw::EntityType::ENTITY_GROUP: {
     846            4 :             ret = AttachQueueInGroup(info.GetId());
     847            4 :             break;
     848              :         }
     849            1 :         default: {
     850            1 :             BQS_LOG_ERROR("Invalid entity[%s]", info.ToString().c_str());
     851            1 :             ret = BQS_STATUS_PARAM_INVALID;
     852            1 :             break;
     853              :         }
     854              :     }
     855           32 :     return ret;
     856              : }
     857              : 
     858            5 : BqsStatus ConfigInfoOperator::AttachQueueInGroup(const uint32_t groupId) const
     859              : {
     860            5 :     auto &entitiesInGroup = BindRelation::GetInstance().GetEntitiesInGroup(groupId);
     861            5 :     if (entitiesInGroup.empty()) {
     862            1 :         BQS_LOG_ERROR("Group[%u] does not exist.", groupId);
     863            1 :         return BQS_STATUS_GROUP_NOT_EXIST;
     864              :     }
     865           13 :     for (const auto &info : entitiesInGroup) {
     866            9 :         if (info == nullptr) {
     867            0 :             BQS_LOG_ERROR("EntityInfo in Group[%u] is nullptr.", groupId);
     868            0 :             return BQS_STATUS_INNER_ERROR;
     869              :         }
     870              :         // endpoints in group is the same type
     871            9 :         if (info->GetType() == dgw::EntityType::ENTITY_QUEUE) {
     872            5 :             const auto drvRet = halQueueAttach(info->GetDeviceId(), info->GetId(), 0);
     873            5 :             if (drvRet != DRV_ERROR_NONE) {
     874            0 :                 BQS_LOG_ERROR("Fail to attach queue[%s] in group[%u], ret[%d]",
     875              :                     info->ToString().c_str(), groupId, static_cast<int32_t>(drvRet));
     876            0 :                 return BQS_STATUS_DRIVER_ERROR;
     877              :             }
     878              :         }
     879              :     }
     880            4 :     return BQS_STATUS_OK;
     881              : }
     882              : 
     883           40 : BqsStatus ConfigInfoOperator::PreprocessUpdateCfgInfo(const uintptr_t mbufData, const uint64_t dataLen)
     884              : {
     885              :     // check and record update config info
     886           40 :     auto ret = CheckAndRecordUpdateCfgInfo(mbufData, dataLen);
     887           40 :     if (ret != BQS_STATUS_OK) {
     888            3 :         BQS_LOG_ERROR("Record update config info failed.");
     889            3 :         return ret;
     890              :     }
     891              : 
     892              :     // attach queue and check queue auth
     893           37 :     ret = CheckFlowQueueAuth();
     894           37 :     if (ret != BQS_STATUS_OK) {
     895            0 :         BQS_LOG_ERROR("Check flow queue auth failed.");
     896            0 :         return ret;
     897              :     }
     898           37 :     return BQS_STATUS_WAIT;
     899              : }
     900              : 
     901           37 : BqsStatus ConfigInfoOperator::CheckFlowQueueAuth() const
     902              : {
     903           37 :     ConfigInfo * const cfgInfo = updateCfgInfo_->cfgInfo;
     904              :     // create group no need attach queue and check queue auth
     905           37 :     if (cfgInfo->cmd == ConfigCmd::DGW_CFG_CMD_BIND_ROUTE) {
     906            7 :         size_t idx = 0UL;
     907           21 :         for (auto &entityPair : updateCfgInfo_->entitiesInRoutes) {
     908              :             // do attach queue and check src own read auth, dst own write auth
     909           14 :             const auto ret = AttachAndCheckQueue(*(entityPair.first), *(entityPair.second));
     910           14 :             if (ret != BQS_STATUS_OK) {
     911            0 :                 BQS_LOG_ERROR("Src[%s] Dst[%s] do attach queue and check auth failed",
     912              :                     entityPair.first->ToString().c_str(), entityPair.second->ToString().c_str());
     913              :             }
     914           14 :             updateCfgInfo_->results[idx]->retCode = static_cast<int32_t>(ret);
     915           14 :             idx++;
     916              :         }
     917              :     }
     918           37 :     return BQS_STATUS_OK;
     919              : }
     920              : 
     921           29 : BqsStatus ConfigInfoOperator::CheckQueueAuth(const EntityInfo &info, const bool isSrc) const
     922              : {
     923           29 :     if (info.GetType() == dgw::EntityType::ENTITY_QUEUE) {
     924           23 :         if (info.GetQueueType() == bqs::CLIENT_Q) {
     925            1 :             return BQS_STATUS_OK;
     926              :         }
     927           22 :         return CheckQueueAuth(info.GetId(), info.GetDeviceId(), isSrc);
     928              :     }
     929            6 :     if (info.GetType() == dgw::EntityType::ENTITY_GROUP) {
     930            4 :         return CheckQueueAuthForGroup(info.GetId(), isSrc);
     931              :     }
     932              :     // else, ENTITY_TAG
     933            2 :     return BQS_STATUS_OK;
     934              : }
     935              : 
     936            5 : BqsStatus ConfigInfoOperator::CheckQueueAuthForGroup(const uint32_t groupId, const bool isSrc) const
     937              : {
     938            5 :     auto &entityVec = BindRelation::GetInstance().GetEntitiesInGroup(groupId);
     939           14 :     for (const auto &entityInfoPtr : entityVec) {
     940           10 :         if (entityInfoPtr == nullptr) {
     941            0 :             BQS_LOG_ERROR("EntityInfo in Group[%u] is nullptr.", groupId);
     942            1 :             return BQS_STATUS_INNER_ERROR;
     943              :         }
     944           10 :         if (entityInfoPtr->GetType() == dgw::EntityType::ENTITY_QUEUE) {
     945            6 :             if (entityInfoPtr->GetQueueType() == bqs::CLIENT_Q) {
     946            1 :                 return BQS_STATUS_OK;
     947              :             }
     948            5 :             const auto ret = CheckQueueAuth(entityInfoPtr->GetId(), entityInfoPtr->GetDeviceId(), isSrc);
     949            5 :             if (ret != BQS_STATUS_OK) {
     950            0 :                 return ret;
     951              :             }
     952              :         }
     953              :     }
     954            4 :     return BQS_STATUS_OK;
     955              : }
     956              : 
     957           27 : BqsStatus ConfigInfoOperator::CheckQueueAuth(const uint32_t queueId, const uint32_t resId, const bool isSrc) const
     958              : {
     959           27 :     std::unique_ptr<QueueQueryOutput> output(new (std::nothrow) QueueQueryOutput());
     960           27 :     if (output == nullptr) {
     961            0 :         BQS_LOG_ERROR("Malloc memory for output failed.");
     962            0 :         return BQS_STATUS_INNER_ERROR;
     963              :     }
     964           27 :     QueueQueryOutputPara outputPara = {output.get(), static_cast<uint32_t>(sizeof(QueueQueryOutput))};
     965           27 :     QueQueryQueueAttr queAttr = {static_cast<int32_t>(queueId)};
     966           27 :     QueueQueryInputPara inputPara = {&queAttr, static_cast<uint32_t>(sizeof(queAttr))};
     967           27 :     const auto drvRet = halQueueQuery(resId, QUEUE_QUERY_QUE_ATTR_OF_CUR_PROC, &inputPara, &outputPara);
     968           27 :     if (drvRet != DRV_ERROR_NONE) {
     969            0 :         BQS_LOG_ERROR("Fail to query queue info, queue[%u], resId[%u], ret[%d]",
     970              :             queueId, resId, static_cast<int32_t>(drvRet));
     971            0 :         return BQS_STATUS_DRIVER_ERROR;
     972              :     }
     973              : 
     974           27 :     const uint32_t authValue = isSrc ? static_cast<uint32_t>(output.get()->queQueryQueueAttrInfo.attr.read) :
     975           13 :         static_cast<uint32_t>(output.get()->queQueryQueueAttrInfo.attr.write);
     976           27 :     if (authValue == 0U) {
     977            0 :         BQS_LOG_ERROR("Queue[%u] res[%u] did not own needed authority, isSrc[%d].",
     978              :             queueId, resId, static_cast<int32_t>(isSrc));
     979            0 :         return BQS_STATUS_QUEUE_AHTU_ERROR;
     980              :     }
     981           27 :     BQS_LOG_INFO("Queue[%u] res[%u] check authority success, isSrc[%d]",
     982              :         queueId, resId, static_cast<int32_t>(isSrc));
     983           27 :     return BQS_STATUS_OK;
     984           27 : }
     985              : 
     986           41 : BqsStatus ConfigInfoOperator::CheckAndRecordUpdateCfgInfo(const uintptr_t mbufData, const uint64_t dataLen)
     987              : {
     988              :     // check min dataLen
     989           41 :     if (dataLen < sizeof(ConfigInfo)) {
     990            1 :         BQS_LOG_ERROR("dataLen[%lu] is invalid.", dataLen);
     991            1 :         return BQS_STATUS_PARAM_INVALID;
     992              :     }
     993              :     // check cfgInfo
     994           40 :     ConfigInfo * const cfgInfo = PtrToPtr<void, ConfigInfo>(ValueToPtr(mbufData));
     995           40 :     if (cfgInfo == nullptr) {
     996            0 :         BQS_LOG_ERROR("cfgInfo is nullptr.");
     997            0 :         return BQS_STATUS_PARAM_INVALID;
     998              :     }
     999              : 
    1000           40 :     updateCfgInfo_.reset(new (std::nothrow) UpdateCfgInfo());
    1001           40 :     if (updateCfgInfo_ == nullptr) {
    1002            0 :         BQS_LOG_ERROR("Malloc memory for updateCfgInfo_ failed.");
    1003            0 :         return BQS_STATUS_INNER_ERROR;
    1004              :     }
    1005              :     // record mbuf data
    1006           40 :     updateCfgInfo_->mbufData = mbufData;
    1007           40 :     updateCfgInfo_->dataLen = dataLen;
    1008              :     // record cfgInfo
    1009           40 :     updateCfgInfo_->cfgInfo = cfgInfo;
    1010              : 
    1011           40 :     BQS_LOG_INFO("cmd is %d", static_cast<int32_t>(cfgInfo->cmd));
    1012           40 :     auto ret = BQS_STATUS_OK;
    1013           40 :     switch (cfgInfo->cmd) {
    1014           13 :         case ConfigCmd::DGW_CFG_CMD_BIND_ROUTE:
    1015              :         case ConfigCmd::DGW_CFG_CMD_UNBIND_ROUTE: {
    1016           13 :             ret = CheckAndRecordRouteInfo();
    1017           13 :             break;
    1018              :         }
    1019           10 :         case ConfigCmd::DGW_CFG_CMD_ADD_GROUP: {
    1020           10 :             ret = CheckAndRecordAddGrpInfo();
    1021           10 :             break;
    1022              :         }
    1023           11 :         case ConfigCmd::DGW_CFG_CMD_UPDATE_PROFILING:
    1024              :         case ConfigCmd::DGW_CFG_CMD_DEL_GROUP:
    1025              :         case ConfigCmd::DGW_CFG_CMD_SET_HCCL_PROTOCOL: {
    1026           11 :             ret = CheckAndRecordCfgInfo();
    1027           11 :             break;
    1028              :         }
    1029            4 :         case ConfigCmd::DGW_CFG_CMD_INIT_DYNAMIC_SCHEDULE: {
    1030            4 :             ret = CheckAndRecordCommonCfg(sizeof(ConfigInfo) + sizeof(DynamicSchedConfigV2));
    1031            4 :             break;
    1032              :         }
    1033            2 :         case ConfigCmd::DGW_CFG_CMD_STOP_SCHEDULE:
    1034              :         case ConfigCmd::DGW_CFG_CMD_CLEAR_AND_RESTART_SCHEDULE: {
    1035            2 :             ret = CheckAndRecordRedeployCfg();
    1036            2 :             break;
    1037              :         }
    1038            0 :         default: {
    1039            0 :             ret = BQS_STATUS_PARAM_INVALID;
    1040            0 :             BQS_LOG_WARN("cmd[%d] is invalid.", static_cast<int32_t>(cfgInfo->cmd));
    1041            0 :             break;
    1042              :         }
    1043              :     }
    1044              : 
    1045              :     // check update config info failed, clear updateCfgInfo_
    1046           40 :     if (ret != BQS_STATUS_OK) {
    1047            3 :         updateCfgInfo_ = nullptr;
    1048              :     }
    1049           40 :     return ret;
    1050              : }
    1051              : 
    1052           13 : BqsStatus ConfigInfoOperator::CheckAndRecordRouteInfo() const
    1053              : {
    1054           13 :     const ConfigInfo * const cfgInfo = updateCfgInfo_->cfgInfo;
    1055           13 :     const size_t routeNum = static_cast<size_t>(cfgInfo->cfg.routesCfg.routeNum);
    1056              :     // check route num
    1057           13 :     if ((routeNum == 0UL) || (routeNum > MAX_ROUTES_NUM)) {
    1058            0 :         BQS_LOG_ERROR("Route num[%zu] is invalid, max allowed value is [%zu].", routeNum, MAX_ROUTES_NUM);
    1059            0 :         return BQS_STATUS_PARAM_INVALID;
    1060              :     }
    1061              :     // calculate and check totalLen
    1062           13 :     const size_t totalLen = sizeof(ConfigInfo) + (routeNum * sizeof(Route)) + (routeNum * sizeof(CfgRetInfo));
    1063           13 :     const uint64_t dataLen = updateCfgInfo_->dataLen;
    1064           13 :     if (totalLen != dataLen) {
    1065            0 :         BQS_LOG_ERROR("dataLen[%lu] is not equal with totalLen[%zu].", dataLen, totalLen);
    1066            0 :         return BQS_STATUS_PARAM_INVALID;
    1067              :     }
    1068              : 
    1069           13 :     auto &routeVec = updateCfgInfo_->routes;
    1070           13 :     auto &resultVec = updateCfgInfo_->results;
    1071           13 :     auto &entityPairVec = updateCfgInfo_->entitiesInRoutes;
    1072           13 :     const uintptr_t routesAddr = updateCfgInfo_->mbufData + sizeof(ConfigInfo);
    1073           13 :     Route * const routes = PtrToPtr<void, Route>(ValueToPtr(routesAddr));
    1074           13 :     CfgRetInfo * const results = PtrToPtr<void, CfgRetInfo>(ValueToPtr(routesAddr + (routeNum * sizeof(Route))));
    1075           40 :     for (size_t idx = 0UL; idx < routeNum; idx++) {
    1076           27 :         Route * const route = PtrAdd<Route>(routes, routeNum, idx);
    1077           27 :         CfgRetInfo * const result = PtrAdd<CfgRetInfo>(results, routeNum, idx);
    1078              :         // initialize retCode
    1079           27 :         result->retCode = static_cast<int32_t>(BQS_STATUS_OK);
    1080           27 :         routeVec.emplace_back(route);
    1081           27 :         resultVec.emplace_back(result);
    1082              :         // create src and dst entity info ptr
    1083           27 :         const EntityInfoPtr src = CreateEntityInfo(route->src, false);
    1084           27 :         const EntityInfoPtr dst = CreateEntityInfo(route->dst, false);
    1085           27 :         if ((src == nullptr) || (dst == nullptr)) {
    1086            0 :             BQS_LOG_ERROR("Create src or dst entityInfoPtr failed.");
    1087            0 :             return BQS_STATUS_INNER_ERROR;
    1088              :         }
    1089           27 :         entityPairVec.emplace_back(std::make_pair(src, dst));
    1090           27 :     }
    1091           13 :     return BQS_STATUS_OK;
    1092              : }
    1093              : 
    1094           12 : BqsStatus ConfigInfoOperator::CheckAndRecordAddGrpInfo() const
    1095              : {
    1096           12 :     const ConfigInfo * const cfgInfo = updateCfgInfo_->cfgInfo;
    1097           12 :     const size_t endpointNum = static_cast<size_t>(cfgInfo->cfg.groupCfg.endpointNum);
    1098              :     // check endpoint num
    1099           12 :     if ((endpointNum == 0UL) || (endpointNum > MAX_ENDPOINTS_NUM_IN_SINGLE_GROUP)) {
    1100            1 :         BQS_LOG_ERROR("Group num[%zu] is invalid, max allowed value is [%u].",
    1101              :             endpointNum, MAX_ENDPOINTS_NUM_IN_SINGLE_GROUP);
    1102            1 :         return BQS_STATUS_PARAM_INVALID;
    1103              :     }
    1104              : 
    1105              :     // calculate and check totalLen
    1106           11 :     const size_t totalLen = sizeof(ConfigInfo) + (endpointNum * sizeof(Endpoint)) + sizeof(CfgRetInfo);
    1107           11 :     const uint64_t dataLen = updateCfgInfo_->dataLen;
    1108           11 :     if (totalLen != dataLen) {
    1109            1 :         BQS_LOG_ERROR("dataLen[%lu] is not equal with totalLen[%zu].", dataLen, totalLen);
    1110            1 :         return BQS_STATUS_PARAM_INVALID;
    1111              :     }
    1112              : 
    1113           10 :     auto &endpointVec = updateCfgInfo_->endpointsInGroup;
    1114           10 :     auto &resultVec = updateCfgInfo_->results;
    1115           10 :     auto &entityVec = updateCfgInfo_->entitiesInGroup;
    1116           10 :     const uintptr_t endpointsAddr = updateCfgInfo_->mbufData + sizeof(ConfigInfo);
    1117           10 :     Endpoint * const endpoints = PtrToPtr<void, Endpoint>(ValueToPtr(endpointsAddr));
    1118           10 :     const uintptr_t results = endpointsAddr + (endpointNum * sizeof(Endpoint));
    1119              :     // only one result
    1120           10 :     CfgRetInfo * const result = PtrToPtr<void, CfgRetInfo>(ValueToPtr(results));
    1121           10 :     resultVec.emplace_back(result);
    1122              : 
    1123           10 :     std::set<std::tuple<const uint32_t, const bool, const uint32_t, const dgw::EntityType>> entitySet;
    1124           27 :     for (size_t idx = 0UL; idx < endpointNum; idx++) {
    1125           20 :         Endpoint * const endpoint = PtrAdd<Endpoint>(endpoints, endpointNum, idx);
    1126           20 :         endpointVec.emplace_back(endpoint);
    1127              :         // create entity info ptr
    1128           20 :         EntityInfoPtr entity = CreateEntityInfo(*endpoint, false);
    1129           20 :         if (entity == nullptr) {
    1130            3 :             BQS_LOG_ERROR("Create entityInfoPtr failed.");
    1131            3 :             return BQS_STATUS_PARAM_INVALID;
    1132              :         }
    1133           17 :         if (entity->GetType() == dgw::EntityType::ENTITY_GROUP) {
    1134            0 :             BQS_LOG_ERROR("Not allowd group[%s] exist in group.", entity->ToString().c_str());
    1135            0 :             return BQS_STATUS_PARAM_INVALID;
    1136              :         }
    1137           17 :         entityVec.emplace_back(entity);
    1138           17 :         uint32_t deviceId = ((endpoint->resId & RESOURCE_ID_ENABLE_BIT_MASK) != 0U) ?
    1139           10 :                              (endpoint->resId & ROUCE_ID_DEVICE_ID_DATA_MASK) : deviceId_;
    1140           17 :         bool isHostQueue = (((endpoint->resId >> RESOURCE_ID_HOST_DEVICE_BIT_NUM) & 1) != 0U) ? true : false;
    1141           17 :         (void)entitySet.emplace(std::make_tuple(deviceId, isHostQueue, entity->GetId(), entity->GetType()));
    1142           20 :     }
    1143              : 
    1144              :     // check whether group has the same entity
    1145            7 :     if (entitySet.size() != endpointNum) {
    1146            0 :         BQS_LOG_ERROR("entitySet size[%lu] is not equal with endpointNum[%lu].", entitySet.size(), endpointNum);
    1147            0 :         return BQS_STATUS_PARAM_INVALID;
    1148              :     }
    1149            7 :     return BQS_STATUS_OK;
    1150           10 : }
    1151              : 
    1152           11 : BqsStatus ConfigInfoOperator::CheckAndRecordCfgInfo() const
    1153              : {
    1154           11 :     return CheckAndRecordCommonCfg(sizeof(ConfigInfo));
    1155              : }
    1156              : 
    1157           18 : BqsStatus ConfigInfoOperator::CheckAndRecordCommonCfg(const size_t resultOffset) const
    1158              : {
    1159              :     // calculate and check totalLen
    1160           18 :     const size_t totalLen = resultOffset + sizeof(CfgRetInfo);
    1161           18 :     const uint64_t dataLen = updateCfgInfo_->dataLen;
    1162           18 :     if (totalLen != dataLen) {
    1163            1 :         BQS_LOG_ERROR("dataLen[%lu] is not equal with totalLen[%zu].", dataLen, totalLen);
    1164            1 :         return BQS_STATUS_PARAM_INVALID;
    1165              :     }
    1166              : 
    1167           17 :     auto &resultVec = updateCfgInfo_->results;
    1168              :     // only one result
    1169           17 :     const uintptr_t results = updateCfgInfo_->mbufData + resultOffset;
    1170           17 :     CfgRetInfo * const result = PtrToPtr<void, CfgRetInfo>(ValueToPtr(results));
    1171           17 :     resultVec.emplace_back(result);
    1172           17 :     BQS_LOG_INFO("CheckAndRecordCommonCfg for %zu", resultOffset);
    1173           17 :     return BQS_STATUS_OK;
    1174              : }
    1175              : 
    1176            2 : BqsStatus ConfigInfoOperator::CheckAndRecordRedeployCfg() const
    1177              : {
    1178            2 :     const ConfigInfo * const cfgInfo = updateCfgInfo_->cfgInfo;
    1179            2 :     const size_t rootModelIdsLen = cfgInfo->cfg.reDeployCfg.rootModelNum * sizeof(uint32_t);
    1180            2 :     return CheckAndRecordCommonCfg(rootModelIdsLen + sizeof(ConfigInfo));
    1181              : }
    1182              : 
    1183           13 : BqsStatus ConfigInfoOperator::ProcessUpdateRoutes(const uint32_t index) const
    1184              : {
    1185              :     // no need to check cfgInfo and updateCfgInfo_ nullptr
    1186           13 :     ConfigInfo * const cfgInfo = updateCfgInfo_->cfgInfo;
    1187           13 :     auto &resultVec = updateCfgInfo_->results;
    1188           13 :     auto &entityPairVec = updateCfgInfo_->entitiesInRoutes;
    1189              : 
    1190           13 :     auto returnCode = BQS_STATUS_OK;
    1191           13 :     size_t idx = 0UL;
    1192           40 :     for (auto &entityPair : entityPairVec) {
    1193              :         // check preprocess result
    1194           27 :         CfgRetInfo * const retInfo = resultVec[idx];
    1195           27 :         idx++;
    1196           27 :         const auto preRet = static_cast<BqsStatus>(retInfo->retCode);
    1197           27 :         if (preRet != BQS_STATUS_OK) {
    1198            0 :             returnCode = preRet;
    1199            0 :             continue;
    1200              :         }
    1201              :         // create entity info
    1202           27 :         const auto ret = (cfgInfo->cmd == ConfigCmd::DGW_CFG_CMD_BIND_ROUTE) ?
    1203           14 :             BindRelation::GetInstance().Bind(*(entityPair.first), *(entityPair.second), index) :
    1204           13 :             BindRelation::GetInstance().UnBind(*(entityPair.first), *(entityPair.second), index);
    1205           27 :         if (ret == BQS_STATUS_RETRY) {
    1206            0 :             continue;
    1207              :         }
    1208              : 
    1209           27 :         retInfo->retCode = static_cast<int32_t>(ret);
    1210           27 :         returnCode = (returnCode == BQS_STATUS_OK) ? ret : returnCode;
    1211           27 :         BQS_LOG_RUN_INFO("Bind/unbind relation operate, cmd[%d], stage[server:process],"
    1212              :             "relation[src:%s, dst:%s, result:%d]", static_cast<int32_t>(cfgInfo->cmd),
    1213              :             entityPair.first->ToString().c_str(), entityPair.second->ToString().c_str(), static_cast<int32_t>(ret));
    1214              :     }
    1215           13 :     BindRelation::GetInstance().Order(index);
    1216           13 :     return returnCode;
    1217              : }
    1218              : 
    1219            7 : BqsStatus ConfigInfoOperator::ProcessAddGroup() const
    1220              : {
    1221              :     // no need to check cfgInfo and updateCfgInfo_ nullptr
    1222              :     // get endpoint number
    1223            7 :     auto cfgInfo = updateCfgInfo_->cfgInfo;
    1224            7 :     auto &resultVec = updateCfgInfo_->results;
    1225            7 :     auto &entityVec = updateCfgInfo_->entitiesInGroup;
    1226              : 
    1227              :     // create group
    1228            7 :     uint32_t groupId = 0U;
    1229            7 :     const auto retCode = BindRelation::GetInstance().CreateGroup(entityVec, groupId);
    1230            7 :     if (retCode == BQS_STATUS_OK) {
    1231            7 :         cfgInfo->cfg.groupCfg.groupId = static_cast<int32_t>(groupId);
    1232              :     }
    1233              :     // set result
    1234            7 :     resultVec[0UL]->retCode = static_cast<int32_t>(retCode);
    1235              : 
    1236            7 :     BQS_LOG_RUN_INFO("Add group operate, cmd[%d], stage[server:process], endpointNum[%zu], groupId[%u], result:[%d]",
    1237              :         static_cast<int32_t>(cfgInfo->cmd), entityVec.size(), groupId, static_cast<int32_t>(retCode));
    1238            7 :     return retCode;
    1239              : }
    1240              : 
    1241            8 : BqsStatus ConfigInfoOperator::ProcessDelGroup() const
    1242              : {
    1243              :     // get endpoint number
    1244            8 :     const auto cfgInfo = updateCfgInfo_->cfgInfo;
    1245            8 :     auto &resultVec = updateCfgInfo_->results;
    1246            8 :     const uint32_t groupId = static_cast<uint32_t>(cfgInfo->cfg.groupCfg.groupId);
    1247              : 
    1248              :     // delete group
    1249            8 :     const auto retCode = BindRelation::GetInstance().DeleteGroup(groupId);
    1250              :     // set result
    1251            8 :     resultVec[0UL]->retCode = static_cast<int32_t>(retCode);
    1252              : 
    1253            8 :     BQS_LOG_RUN_INFO("Delete group operate, cmd[%d], stage[server:process], groupId[%u], result:[%d]",
    1254              :         static_cast<int32_t>(cfgInfo->cmd), groupId, static_cast<int32_t>(retCode));
    1255            8 :     return retCode;
    1256              : }
    1257              : 
    1258            1 : BqsStatus ConfigInfoOperator::ProcessUpdateProfiling() const
    1259              : {
    1260              :     // get prof mode
    1261            1 :     const auto cfgInfo = updateCfgInfo_->cfgInfo;
    1262            1 :     auto &resultVec = updateCfgInfo_->results;
    1263            1 :     const ProfilingMode mode = cfgInfo->cfg.profCfg.profMode;
    1264              :     // set prof mode
    1265            1 :     auto retCode = ProfileManager::GetInstance(0U).UpdateProfilingMode(mode);
    1266            1 :     if ((retCode == BQS_STATUS_OK) && GlobalCfg::GetInstance().GetNumaFlag()) {
    1267            0 :         retCode = bqs::ProfileManager::GetInstance(1U).UpdateProfilingMode(mode);
    1268              :     }
    1269              :     // set result
    1270            1 :     resultVec[0UL]->retCode = static_cast<int32_t>(retCode);
    1271            1 :     BQS_LOG_RUN_INFO("Update profiling operate, cmd[%d], stage[server:process], profiling mode[%u], result:[%d]",
    1272              :         static_cast<int32_t>(cfgInfo->cmd), static_cast<uint32_t>(mode), static_cast<int32_t>(retCode));
    1273            1 :     return retCode;
    1274              : }
    1275              : 
    1276            2 : BqsStatus ConfigInfoOperator::ProcessUpdateHcclProtocol() const
    1277              : {
    1278            2 :     const auto cfgInfo = updateCfgInfo_->cfgInfo;
    1279            2 :     auto &resultVec = updateCfgInfo_->results;
    1280            2 :     const HcclProtocolType protocol = cfgInfo->cfg.hcclProtocolCfg.protocol;
    1281              : 
    1282              :     // set protocol
    1283            2 :     auto retCode = BQS_STATUS_OK;
    1284            2 :     std::string strProtocol = "";
    1285            2 :     if (protocol == HcclProtocolType::RDMA) {
    1286            1 :         strProtocol = "RDMA";
    1287            1 :     } else if (protocol == HcclProtocolType::TCP) {
    1288            1 :         strProtocol = "TCP";
    1289              :     } else {
    1290            0 :         BQS_LOG_ERROR("Invalid protocol type[%d]", static_cast<int32_t>(protocol));
    1291            0 :         retCode = BQS_STATUS_PARAM_INVALID;
    1292              :     }
    1293              : 
    1294            2 :     if (!strProtocol.empty()) {
    1295            2 :         const auto ret = setenv("HCCL_NPU_NET_PROTOCOL", strProtocol.c_str(), 1);
    1296            2 :         if (ret != 0) {
    1297            0 :             BQS_LOG_ERROR("setenv HCCL_NPU_NET_PROTOCOL failed, ret[%d]", ret);
    1298            0 :             retCode = BQS_STATUS_INNER_ERROR;
    1299              :         }
    1300              :     }
    1301              :     // set result
    1302            2 :     resultVec[0UL]->retCode = static_cast<int32_t>(retCode);
    1303            2 :     BQS_LOG_RUN_INFO("Update hccl_protocol operate, cmd[%d], stage[server:process], protocol[%d], result:[%d]",
    1304              :         static_cast<int32_t>(cfgInfo->cmd), static_cast<int32_t>(protocol), static_cast<int32_t>(retCode));
    1305            2 :     return retCode;
    1306            2 : }
    1307              : 
    1308            4 : BqsStatus ConfigInfoOperator::ProcessInitDynamicSched() const
    1309              : {
    1310            4 :     BQS_LOG_INFO("ProcessInitDynamicSched");
    1311            4 :     const auto cfgInfo = updateCfgInfo_->cfgInfo;
    1312            4 :     auto &resultVec = updateCfgInfo_->results;
    1313              : 
    1314            4 :     const uintptr_t dynamicSchedCfgAddr = updateCfgInfo_->mbufData + sizeof(ConfigInfo);
    1315              :     const DynamicSchedConfigV2 * const dynamicCfg =
    1316            4 :         PtrToPtr<void, DynamicSchedConfigV2>(ValueToPtr(dynamicSchedCfgAddr));
    1317              : 
    1318            4 :     BqsStatus retCode = BQS_STATUS_OK;
    1319            4 :     uint32_t localRequestQDeviceId = ParseDeviceId(dynamicCfg->requestQ.deviceId);
    1320            4 :     uint32_t localResponseDeviceId = ParseDeviceId(dynamicCfg->responseQ.deviceId);
    1321              : 
    1322            4 :     auto drvRet = halQueueAttach(localRequestQDeviceId, dynamicCfg->requestQ.queueId, 0);
    1323            4 :     if (drvRet != DRV_ERROR_NONE) {
    1324            2 :         BQS_LOG_ERROR("Fail to attach queue[%u], device[%u], ret[%d]", dynamicCfg->requestQ.queueId,
    1325              :                       localRequestQDeviceId, static_cast<int32_t>(drvRet));
    1326            2 :         resultVec[0UL]->retCode = static_cast<int32_t>(BQS_STATUS_DRIVER_ERROR);
    1327            2 :         return BQS_STATUS_DRIVER_ERROR;
    1328              :     }
    1329            2 :     drvRet = halQueueAttach(localResponseDeviceId, dynamicCfg->responseQ.queueId, 0);
    1330            2 :     if (drvRet != DRV_ERROR_NONE) {
    1331            1 :         BQS_LOG_ERROR("Fail to attach queue[%u], device[%u], ret[%d]", dynamicCfg->responseQ.queueId,
    1332              :                       localResponseDeviceId, static_cast<int32_t>(drvRet));
    1333            1 :         resultVec[0UL]->retCode = static_cast<int32_t>(BQS_STATUS_DRIVER_ERROR);
    1334            1 :         return BQS_STATUS_DRIVER_ERROR;
    1335              :     }
    1336              : 
    1337            1 :     dgw::DynamicSchedMgr::RootModelInfo schedCfgInfo = {};
    1338            1 :     schedCfgInfo.rootModelId = dynamicCfg->rootModelId;
    1339            1 :     schedCfgInfo.requestQue = dynamicCfg->requestQ;
    1340            1 :     schedCfgInfo.requestQue.deviceId = localRequestQDeviceId;
    1341            1 :     schedCfgInfo.responseQue = dynamicCfg->responseQ;
    1342            1 :     schedCfgInfo.responseQue.deviceId = localResponseDeviceId;
    1343              : 
    1344            1 :     uint32_t resIndex = 0U;
    1345            1 :     if (GlobalCfg::GetInstance().GetNumaFlag()) {
    1346            1 :         resIndex = GlobalCfg::GetInstance().GetResIndexByDeviceId(localRequestQDeviceId);
    1347              :     }
    1348            1 :     const auto addCfgRet = dgw::DynamicSchedMgr::GetInstance(resIndex).AddRootModelInfo(schedCfgInfo);
    1349            1 :     if (addCfgRet != dgw::FsmStatus::FSM_SUCCESS) {
    1350            0 :         BQS_LOG_ERROR("Fail to add dynamic sched config, rootModelId[%u], ret[%d]", schedCfgInfo.rootModelId,
    1351              :             static_cast<int32_t>(addCfgRet));
    1352            0 :         resultVec[0UL]->retCode = static_cast<int32_t>(BQS_STATUS_DYNAMIC_SCHEDULE_ERROR);
    1353            0 :         return BQS_STATUS_DYNAMIC_SCHEDULE_ERROR;
    1354              :     }
    1355              : 
    1356              :     QueueSetInputPara inPutParam;
    1357              :     QueueSetInput inPut;
    1358            1 :     inPut.queSetWorkMode.qid = schedCfgInfo.responseQue.queueId;
    1359            1 :     inPut.queSetWorkMode.workMode = QUEUE_MODE_PUSH;
    1360            1 :     inPutParam.inBuff = static_cast<void *>(&inPut);
    1361            1 :     inPutParam.inLen = static_cast<uint32_t>(sizeof(QueueSetInput));
    1362            1 :     drvRet = halQueueSet(0U, QUEUE_SET_WORK_MODE, &inPutParam);
    1363            1 :     BQS_LOG_RUN_INFO("Set queue[%u] work mode to push for dynamic schedule.", schedCfgInfo.responseQue.queueId);
    1364              : 
    1365            1 :     if ((SubscribeQueueEvent(!schedCfgInfo.requestQue.isClientQ, schedCfgInfo.requestQue.queueId,
    1366            2 :         schedCfgInfo.requestQue.deviceId, resIndex, false) != BQS_STATUS_OK) ||
    1367            1 :         (SubscribeQueueEvent(!schedCfgInfo.responseQue.isClientQ, schedCfgInfo.responseQue.queueId,
    1368              :         schedCfgInfo.responseQue.deviceId, resIndex, true) != BQS_STATUS_OK)) {
    1369            0 :         BQS_LOG_ERROR("Fail to subscribe enque event of [qid:%u-deviceId:%u-isclientQ:%d] or "
    1370              :             "subscribe f2nf of [qid:%u-deviceId:%u-isclientQ:%d]",
    1371              :             schedCfgInfo.responseQue.queueId, schedCfgInfo.responseQue.deviceId, schedCfgInfo.responseQue.isClientQ,
    1372              :             schedCfgInfo.requestQue.queueId, schedCfgInfo.requestQue.deviceId, schedCfgInfo.responseQue.isClientQ);
    1373            0 :         resultVec[0UL]->retCode = static_cast<int32_t>(BQS_STATUS_INNER_ERROR);
    1374            0 :         return BQS_STATUS_INNER_ERROR;
    1375              :     }
    1376            1 :     dgw::ScheduleConfig::GetInstance().
    1377            1 :         RecordConfig(dynamicCfg->rootModelId, schedCfgInfo.requestQue, schedCfgInfo.responseQue);
    1378              : 
    1379              :     // set result
    1380            1 :     resultVec[0UL]->retCode = static_cast<int32_t>(retCode);
    1381            1 :     BQS_LOG_RUN_INFO("Init dynamicSched[%u] operate, cmd[%d], stage[server:process], rootModelId[%u], result:[%d]",
    1382              :         localRequestQDeviceId, static_cast<int32_t>(cfgInfo->cmd), dynamicCfg->rootModelId,
    1383              :         static_cast<int32_t>(retCode));
    1384            1 :     return retCode;
    1385            1 : }
    1386              : 
    1387            8 : uint32_t ConfigInfoOperator::ParseDeviceId(const uint32_t rawDeviceId) const
    1388              : {
    1389            8 :     uint32_t localDeviceId = rawDeviceId;
    1390            8 :     if ((bqs::GetRunContext() != bqs::RunContext::HOST) && (&drvGetLocalDevIDByHostDevID != nullptr)) {
    1391            0 :         auto retCode = drvGetLocalDevIDByHostDevID(rawDeviceId, &localDeviceId);
    1392            0 :         if (retCode != static_cast<int32_t>(DRV_ERROR_NONE)) {
    1393            0 :             BQS_LOG_INFO("host devid(%u) transform to local devid not success.", rawDeviceId);
    1394            0 :             localDeviceId = rawDeviceId;
    1395              :         }
    1396              :     }
    1397            8 :     return localDeviceId;
    1398              : }
    1399              : 
    1400            2 : BqsStatus ConfigInfoOperator::SubscribeQueueEvent(const bool isLocalQ, const uint32_t queueId, const uint32_t deviceId,
    1401              :     const uint32_t resIndex, const bool isEnqueue) const
    1402              : {
    1403            2 :     const auto subscribeManager = Subscribers::GetInstance().GetSubscribeManager(resIndex, deviceId);
    1404            2 :     if (subscribeManager == nullptr) {
    1405            0 :         BQS_LOG_ERROR("Failed to find subscribeManager for isLocalQ:%d, device: %u, resIndex: %u",
    1406              :             static_cast<int32_t>(isLocalQ), deviceId, resIndex);
    1407            0 :         return BQS_STATUS_INNER_ERROR;
    1408              :     }
    1409            2 :     return isEnqueue ? subscribeManager->Subscribe(queueId) :
    1410            2 :         subscribeManager->SubscribeFullToNotFull(queueId);
    1411              : }
    1412              : 
    1413            8 : BqsStatus ConfigInfoOperator::CheckCommChannelAttr(const CommChannelAttr &attr, const bool isQry) const
    1414              : {
    1415            8 :     if (attr.localTagId != attr.peerTagId) {
    1416            1 :         BQS_LOG_ERROR("Local tag id[%u] is not equal with peer tag id[%u]. Please check!",
    1417              :             attr.localTagId, attr.peerTagId);
    1418            1 :         return BQS_STATUS_PARAM_INVALID;
    1419              :     }
    1420            7 :     if (attr.localRankId == attr.peerRankId) {
    1421            1 :         BQS_LOG_ERROR("local rank id[%u] is equal with peer rank id[%u]. Please check!",
    1422              :             attr.localRankId, attr.peerRankId);
    1423            1 :         return BQS_STATUS_PARAM_INVALID;
    1424              :     }
    1425            6 :     if (isQry) {
    1426            0 :         return BQS_STATUS_OK;
    1427              :     }
    1428              :     // when qry route, no need check tag depth
    1429            6 :     if ((attr.localTagDepth == 0U) || (attr.localTagDepth > MAX_TAG_DEPTH)) {
    1430            1 :         BQS_LOG_ERROR("Local tag depth[%u] is invalid, max tag depth is [%u].", attr.localTagDepth, MAX_TAG_DEPTH);
    1431            1 :         return BQS_STATUS_PARAM_INVALID;
    1432              :     }
    1433            5 :     if ((attr.peerTagDepth == 0U) || (attr.peerTagDepth > MAX_TAG_DEPTH)) {
    1434            0 :         BQS_LOG_ERROR("Peer tag depth[%u] is invalid, max tag depth is [%u].", attr.peerTagDepth, MAX_TAG_DEPTH);
    1435            0 :         return BQS_STATUS_PARAM_INVALID;
    1436              :     }
    1437            5 :     return BQS_STATUS_OK;
    1438              : }
    1439              : 
    1440            1 : BqsStatus ConfigInfoOperator::ProcessStopSchedule(const uint32_t index) const
    1441              : {
    1442            1 :     BQS_LOG_RUN_INFO("ProcessStopSchedule");
    1443            1 :     const auto cfgInfo = updateCfgInfo_->cfgInfo;
    1444            1 :     auto &resultVec = updateCfgInfo_->results;
    1445              : 
    1446            1 :     const uintptr_t rootModelIdsAddr = updateCfgInfo_->mbufData + sizeof(ConfigInfo);
    1447            1 :     const uint32_t * const rootModelIds = PtrToPtr<void, uint32_t>(ValueToPtr(rootModelIdsAddr));
    1448            1 :     const uint32_t rootModelNum = cfgInfo->cfg.reDeployCfg.rootModelNum;
    1449              : 
    1450            1 :     if ((rootModelNum != 0U) && (rootModelIds == nullptr)) {
    1451            0 :         BQS_LOG_ERROR("Invalid rootModelIds");
    1452            0 :         resultVec[0UL]->retCode = static_cast<int32_t>(BQS_STATUS_PARAM_INVALID);
    1453            0 :         return BQS_STATUS_PARAM_INVALID;
    1454              :     }
    1455              : 
    1456            1 :     std::unordered_set<uint32_t> rootModelSet;
    1457            2 :     for (uint32_t i = 0U; i < rootModelNum; i++) {
    1458            1 :         dgw::ScheduleConfig::GetInstance().StopSched(rootModelIds[i]);
    1459            1 :         rootModelSet.insert(rootModelIds[i]);
    1460              :     }
    1461            1 :     (void)dgw::DynamicSchedMgr::GetInstance(index).ClearCacheRouteResult();
    1462              : 
    1463            1 :     const auto retCode = BindRelation::GetInstance().MakeSureOutputCompletion(index, rootModelSet);
    1464              : 
    1465            1 :     resultVec[0UL]->retCode = static_cast<int32_t>(retCode);
    1466            1 :     BQS_LOG_RUN_INFO("Finish ProcessStopSchedule, retCode is %d", static_cast<int32_t>(retCode));
    1467            1 :     return retCode;
    1468            1 : }
    1469              : 
    1470            1 : BqsStatus ConfigInfoOperator::ProcessRestartSchedule(const uint32_t index) const
    1471              : {
    1472            1 :     BQS_LOG_RUN_INFO("ProcessRestartSchedule");
    1473            1 :     const auto cfgInfo = updateCfgInfo_->cfgInfo;
    1474            1 :     auto &resultVec = updateCfgInfo_->results;
    1475              : 
    1476            1 :     const uintptr_t rootModelIdsAddr = updateCfgInfo_->mbufData + sizeof(ConfigInfo);
    1477            1 :     const uint32_t * const rootModelIds = PtrToPtr<void, uint32_t>(ValueToPtr(rootModelIdsAddr));
    1478            1 :     const uint32_t rootModelNum = cfgInfo->cfg.reDeployCfg.rootModelNum;
    1479              : 
    1480            1 :     if ((rootModelNum != 0U) && (rootModelIds == nullptr)) {
    1481            0 :         BQS_LOG_ERROR("Invalid rootModelIds");
    1482            0 :         resultVec[0UL]->retCode = static_cast<int32_t>(BQS_STATUS_PARAM_INVALID);
    1483            0 :         return BQS_STATUS_PARAM_INVALID;
    1484              :     }
    1485              : 
    1486            1 :     std::unordered_set<uint32_t> rootModelSet;
    1487            2 :     for (uint32_t i = 0U; i < rootModelNum; i++) {
    1488            1 :         rootModelSet.insert(rootModelIds[i]);
    1489              :     }
    1490            1 :     const auto ret = BindRelation::GetInstance().ClearInputQueue(index, rootModelSet);
    1491            1 :     if (ret == BQS_STATUS_OK) {
    1492            1 :         std::vector<dgw::DynamicSchedMgr::ResponseInfo> responses;
    1493            2 :         for (uint32_t i = 0U; i < rootModelNum; i++) {
    1494              :             do {
    1495            1 :                 responses.clear();
    1496            1 :                 (void)dgw::DynamicSchedMgr::GetInstance(index).GetResponse(rootModelIds[i], responses);
    1497            1 :             } while (!responses.empty());
    1498            1 :             dgw::ScheduleConfig::GetInstance().RestartSched(rootModelIds[i]);
    1499              :         }
    1500            1 :     }
    1501            1 :     resultVec[0UL]->retCode = static_cast<int32_t>(ret);
    1502            1 :     BQS_LOG_RUN_INFO("Finish ProcessRestartSchedule");
    1503            1 :     return ret;
    1504            1 : }
    1505              : }
        

Generated by: LCOV version 2.0-1