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 "tp_mgr.h"
12 :
13 : #include <algorithm>
14 : #include <vector>
15 :
16 : #include "hccp_ctx.h"
17 : #include "hccp_async_ctx.h"
18 :
19 : #include "hccl_common.h"
20 : #include "exception_handler.h"
21 : #include "network_api_exception.h"
22 : #include "orion_adapter_hccp.h"
23 : #include "rdma_handle_manager.h"
24 : #include "dev_type.h"
25 : #include "orion_adapter_rts.h"
26 : #include "env_config/env_config_v2.h"
27 : #include "tp_qos.h"
28 :
29 : namespace hcomm {
30 :
31 : namespace {
32 : constexpr uint32_t kTpAttrSlAvailableBit = 17U;
33 : static constexpr uint32_t kTpAttrBitmapSl = (1U << 10U);
34 : static constexpr uint32_t kTpAttrBitmapDscp = (1U << 8U);
35 : static constexpr uint32_t kTpAttrDscpConfigModeBit = 18U;
36 :
37 1824 : static constexpr QosKey QosMapKey(uint32_t qos) noexcept { return static_cast<QosKey>(qos & 0xFFU); }
38 :
39 : // MAINBOARD_PCIE_STD(PCIE 标卡):跳过 GetTpAttr/SL 策略,固定使用 TP 列表首个 TP;
40 : // jetty priority(SL)取 2,为标卡 UB 互通方案约定档位,与现网标卡环境对齐。
41 : static constexpr uint32_t kPcieStdMappedSl = 2U;
42 :
43 687 : static HcclResult IsPcieStdMainboardByPhyId(uint32_t devPhyId, bool& isPcieStd)
44 : {
45 687 : isPcieStd = false;
46 687 : u32 devLogicId = 0U;
47 687 : CHK_RET(hrtGetDeviceIndexByPhyId(devPhyId, devLogicId));
48 687 : Hccl::HcclMainboardId mainboardId = Hccl::HcclMainboardId::MAINBOARD_OTHERS;
49 687 : CHK_RET(Hccl::HrtGetMainboardId(devLogicId, mainboardId));
50 687 : isPcieStd = (mainboardId == Hccl::HcclMainboardId::MAINBOARD_PCIE_STD);
51 687 : return HcclResult::HCCL_SUCCESS;
52 : }
53 :
54 : struct TpInfoAddrKey {
55 : Hccl::IpAddress locAddr{};
56 : Hccl::IpAddress rmtAddr{};
57 : QosKey qosKey{0};
58 : };
59 :
60 1595 : static HcclResult ResolveTpInfoAddrKey(const GetTpInfoParam& param, TpInfoAddrKey& out)
61 : {
62 1595 : CHK_RET(CommAddrToIpAddress(param.locAddr, out.locAddr));
63 1595 : CHK_RET(CommAddrToIpAddress(param.rmtAddr, out.rmtAddr));
64 1595 : out.qosKey = QosMapKey(param.qos);
65 1595 : return HcclResult::HCCL_SUCCESS;
66 : }
67 :
68 458 : static uint32_t CalSlAvailableCnt(uint32_t mask)
69 : {
70 458 : uint32_t c = 0;
71 7786 : for (uint32_t i = 0; i < 16U; ++i) {
72 7328 : if ((mask & (1U << i)) != 0U) {
73 1366 : ++c;
74 : }
75 : }
76 458 : return c;
77 : }
78 :
79 229 : static uint32_t SlValueAtRankInMask16(uint32_t mask, uint32_t rank)
80 : {
81 229 : uint32_t seen = 0;
82 294 : for (uint32_t bit = 0; bit < 16U; ++bit) {
83 294 : if ((mask & (1U << bit)) != 0U) {
84 259 : if (seen == rank) {
85 229 : return bit;
86 : }
87 30 : ++seen;
88 : }
89 : }
90 0 : return 0;
91 : }
92 :
93 236 : static uint16_t ReadSlAvailableMask16(const struct TpAttr& attr) { return static_cast<uint16_t>(attr.slBitmap); }
94 :
95 229 : static uint32_t ResolveSlAvailableCntForPolicy(uint16_t slMask, uint32_t slLevelCount)
96 : {
97 229 : uint32_t slAvailableCnt = CalSlAvailableCnt(slMask);
98 229 : if (slLevelCount != 0U) {
99 1 : slAvailableCnt = std::min(slLevelCount, slAvailableCnt);
100 : }
101 229 : return slAvailableCnt;
102 : }
103 :
104 : static bool
105 229 : ApplyQosTpSlPolicy(const GetTpInfoParam& param, uint16_t slMask, uint32_t& tpListIndexOut, uint32_t& mappedSlOut)
106 : {
107 229 : const uint32_t slAvailableCnt = ResolveSlAvailableCntForPolicy(slMask, param.slLevelCount);
108 229 : if (slAvailableCnt == 0U) {
109 0 : return false;
110 : }
111 229 : if (param.loopFirstTpLowestSl) {
112 204 : tpListIndexOut = 0U;
113 204 : mappedSlOut = SlValueAtRankInMask16(slMask, 0U);
114 204 : return true;
115 : }
116 :
117 25 : const uint32_t qos = param.qos;
118 25 : const uint32_t numGroups = slAvailableCnt;
119 25 : const uint32_t groupIdx = Hccl::TpQosResolveQosSlGroupIdx(qos, numGroups);
120 25 : if (groupIdx >= numGroups) {
121 0 : HCCL_ERROR(
122 : "[TpMgr][%s] groupIdx out of range: groupIdx[%u] numGroups[%u] qos[%u] slAvailableCnt[%u].", __func__,
123 : groupIdx, numGroups, qos, slAvailableCnt);
124 0 : return false;
125 : }
126 :
127 25 : tpListIndexOut = 0U;
128 25 : const uint32_t slRank = (slAvailableCnt - 1U) - groupIdx;
129 25 : mappedSlOut = SlValueAtRankInMask16(slMask, slRank);
130 25 : return true;
131 : }
132 :
133 7 : static uint8_t ResolveUboeDscpLookupQos(const GetTpInfoParam& param, uint32_t nTp, uint16_t slMask)
134 : {
135 : (void)nTp;
136 : (void)slMask;
137 7 : if (param.loopFirstTpLowestSl) {
138 1 : return 0U;
139 : }
140 6 : return static_cast<uint8_t>(param.qos & 0xFFU);
141 : }
142 :
143 : /// isSync=false(异步 GetTpInfo 写回 SL/DSCP):HrtRaSetTpAttrAsync。
144 : /// 阻塞等待在 adapter 内(RaSetTpAttrAsync + WaitRequestResult),本函数返回时 Set 已生效。
145 : /// 不用 RaCtxSetTpAttr,避免 Rs 路径 phyId 无效(与 TpManager::SetTpAttrAsync 一致)。
146 232 : static HcclResult SetTpAttrAsync(
147 : const Hccl::RdmaHandle rdmaHandle, uint64_t tpHandle, uint32_t attrBitmap, struct TpAttr& attr,
148 : const char* logTag)
149 : {
150 232 : Hccl::RequestHandle reqHandle = 0;
151 : try {
152 232 : const HcclResult hret = Hccl::HrtRaSetTpAttrAsync(rdmaHandle, tpHandle, attrBitmap, attr, reqHandle);
153 232 : if (hret != HcclResult::HCCL_SUCCESS) {
154 0 : HCCL_ERROR(
155 : "[TpMgr][%s] HrtRaSetTpAttrAsync failed hcclRet[%d] tpHandle[%llu].", logTag,
156 : static_cast<int>(hret), static_cast<unsigned long long>(tpHandle));
157 : }
158 232 : return hret;
159 0 : } catch (const Hccl::NetworkApiException& ex) {
160 0 : HCCL_ERROR(
161 : "[TpMgr][%s] HrtRaSetTpAttrAsync exception: %s tpHandle[%llu].", logTag, ex.what(),
162 : static_cast<unsigned long long>(tpHandle));
163 0 : return HcclResult::HCCL_E_NETWORK;
164 0 : }
165 : }
166 :
167 : static HcclResult
168 225 : CommitMappedSlToTpAttr(const uint32_t devPhyId, const CommAddr& locCommAddr, uint64_t tpHandle, uint32_t mappedSl)
169 : {
170 225 : if (tpHandle == 0U) {
171 0 : HCCL_ERROR("[TpMgr][CommitMappedSlToTpAttr] tpHandle is 0");
172 0 : return HcclResult::HCCL_E_INTERNAL;
173 : }
174 225 : Hccl::IpAddress locAddr{};
175 225 : CHK_RET(CommAddrToIpAddress(locCommAddr, locAddr));
176 225 : const Hccl::RdmaHandle rdmaHandle = Hccl::RdmaHandleManager::GetInstance().GetByIp(devPhyId, locAddr);
177 225 : CHK_PTR_NULL(rdmaHandle);
178 :
179 225 : struct TpAttr tpSlAttr {};
180 225 : tpSlAttr.sl = static_cast<uint8_t>(mappedSl & 0xFU);
181 : const HcclResult hret
182 225 : = SetTpAttrAsync(rdmaHandle, tpHandle, kTpAttrBitmapSl, tpSlAttr, "CommitMappedSlToTpAttr");
183 225 : if (hret == HcclResult::HCCL_SUCCESS) {
184 225 : HCCL_INFO(
185 : "[TpMgr][CommitMappedSlToTpAttr] ok tpHandle[%llu] sl[%u].", static_cast<unsigned long long>(tpHandle),
186 : static_cast<unsigned>(mappedSl & 0xFU));
187 : }
188 225 : return hret;
189 : }
190 :
191 : static HcclResult
192 7 : CommitUboeDscpToTpAttr(const uint32_t devPhyId, const CommAddr& locCommAddr, uint64_t tpHandle, uint8_t dscp)
193 : {
194 7 : if (tpHandle == 0U) {
195 0 : HCCL_ERROR("[TpMgr][CommitUboeDscpToTpAttr] tpHandle is 0");
196 0 : return HcclResult::HCCL_E_INTERNAL;
197 : }
198 7 : Hccl::IpAddress locAddr{};
199 7 : CHK_RET(CommAddrToIpAddress(locCommAddr, locAddr));
200 7 : const Hccl::RdmaHandle rdmaHandle = Hccl::RdmaHandleManager::GetInstance().GetByIp(devPhyId, locAddr);
201 7 : CHK_PTR_NULL(rdmaHandle);
202 :
203 7 : struct TpAttr tpDscpAttr {};
204 7 : tpDscpAttr.dscp = static_cast<uint8_t>(dscp & 0x3FU);
205 : const HcclResult hret
206 7 : = SetTpAttrAsync(rdmaHandle, tpHandle, kTpAttrBitmapDscp, tpDscpAttr, "CommitUboeDscpToTpAttr");
207 7 : if (hret == HcclResult::HCCL_SUCCESS) {
208 7 : HCCL_INFO(
209 : "[TpMgr][CommitUboeDscpToTpAttr] ok tpHandle[%llu] dscp[%u].",
210 : static_cast<unsigned long long>(tpHandle), static_cast<unsigned>(tpDscpAttr.dscp));
211 : }
212 7 : return hret;
213 : }
214 :
215 : } // namespace
216 :
217 863 : TpMgr& TpMgr::GetInstance(const uint32_t devicePhyId)
218 : {
219 995 : static TpMgr tpMgr[MAX_MODULE_DEVICE_NUM + 1];
220 :
221 863 : uint32_t devPhyId = devicePhyId;
222 863 : if (devPhyId >= MAX_MODULE_DEVICE_NUM) {
223 1 : HCCL_WARNING(
224 : "[TpMgr][%s] use the backup device, devPhyId[%u] should be "
225 : "less than %u.",
226 : __func__, devPhyId, MAX_MODULE_DEVICE_NUM);
227 1 : devPhyId = MAX_MODULE_DEVICE_NUM;
228 : }
229 :
230 863 : tpMgr[devPhyId].devPhyId_ = devPhyId;
231 :
232 863 : return tpMgr[devPhyId];
233 : }
234 :
235 560 : static HcclResult CheckRequestResult(RequestHandle& reqHandle)
236 : {
237 560 : if (reqHandle == 0) {
238 0 : return HcclResult::HCCL_SUCCESS;
239 : }
240 :
241 560 : RequestResult result = HccpGetAsyncReqResult(reqHandle);
242 560 : if (result == RequestResult::NOT_COMPLETED) {
243 0 : return HcclResult::HCCL_E_AGAIN;
244 : }
245 :
246 560 : if (result != RequestResult::COMPLETED) {
247 0 : HCCL_ERROR("[TpMgr][%s] failed, result[%s] is unexpected.", __func__, result.Describe().c_str());
248 0 : return HcclResult::HCCL_E_NETWORK;
249 : }
250 :
251 560 : return HcclResult::HCCL_SUCCESS;
252 : }
253 :
254 692 : HcclResult CheckTpProtocol(const TpProtocol tpProtocol)
255 : {
256 692 : if (tpProtocol != TpProtocol::CTP && tpProtocol != TpProtocol::RTP && tpProtocol != TpProtocol::UBOE) {
257 1 : HCCL_ERROR("[TpMgr][%s] failed, tpProtocol[%s] is not supported.", __func__, tpProtocol.Describe().c_str());
258 1 : return HcclResult::HCCL_E_NOT_SUPPORT;
259 : }
260 :
261 691 : return HcclResult::HCCL_SUCCESS;
262 : }
263 :
264 908 : HcclResult TpMgr::LookupInfoCtxEntry(
265 : InfoCtxMap& infoMap, const Hccl::IpAddress& locAddr, const Hccl::IpAddress& rmtAddr, const QosKey qosKey,
266 : InfoCtxMap::iterator& lit, InfoRmtMap::iterator& rit, InfoQosMap::iterator& qosIt) const
267 : {
268 908 : lit = infoMap.find(locAddr);
269 908 : if (lit == infoMap.end()) {
270 690 : return HcclResult::HCCL_E_NOT_FOUND;
271 : }
272 218 : rit = lit->second.find(rmtAddr);
273 218 : if (rit == lit->second.end()) {
274 0 : return HcclResult::HCCL_E_NOT_FOUND;
275 : }
276 218 : qosIt = rit->second.find(qosKey);
277 218 : if (qosIt == rit->second.end()) {
278 4 : return HcclResult::HCCL_E_NOT_FOUND;
279 : }
280 214 : return HcclResult::HCCL_SUCCESS;
281 : }
282 :
283 691 : HcclResult TpMgr::FindAndGetTpInfo(const GetTpInfoParam& param, TpInfo& tpInfo)
284 : {
285 691 : TpInfoAddrKey key{};
286 691 : CHK_RET(ResolveTpInfoAddrKey(param, key));
287 691 : std::lock_guard<std::mutex> lock(GetInfoCtxMutex(param.tpProtocol));
288 691 : auto& infoMap = GetInfoCtxMap(param.tpProtocol);
289 691 : InfoCtxMap::iterator lit;
290 691 : InfoRmtMap::iterator rit;
291 691 : InfoQosMap::iterator qosIt;
292 691 : const auto lookupRet = LookupInfoCtxEntry(infoMap, key.locAddr, key.rmtAddr, key.qosKey, lit, rit, qosIt);
293 691 : if (lookupRet != HcclResult::HCCL_SUCCESS) {
294 687 : return lookupRet;
295 : }
296 : // 复用缓存:useCnt 仅在此处(命中)递增,与 CommitTpInfoToCache 写入路径分离。
297 4 : qosIt->second.useCnt += 1;
298 4 : tpInfo = qosIt->second.tpInfo;
299 4 : return HcclResult::HCCL_SUCCESS;
300 691 : }
301 :
302 229 : HcclResult TpMgr::BeginGetTpInfoListRequest(const GetTpInfoParam& param, ReqQosMap& qosMap, const QosKey qosKey)
303 : {
304 229 : RequestCtx& reqCtx = qosMap[qosKey];
305 229 : CHK_RET(StartGetTpInfoListRequest(param, reqCtx));
306 229 : HCCL_INFO(
307 : "[TpMgr][GetTpInfo] RaGetTpInfoListAsync submitted, devPhyId[%u] reqHandle[%llu] phase[WAIT_LIST] "
308 : "param[%s].",
309 : devPhyId_, static_cast<unsigned long long>(reqCtx.handle), param.Describe().c_str());
310 229 : return HcclResult::HCCL_E_AGAIN;
311 : }
312 :
313 229 : HcclResult TpMgr::AdvanceGetTpInfoWaitList(
314 : const GetTpInfoParam& param, RequestCtx& reqCtx, ReqQosMap& qosMap, const ReqQosMap::iterator it,
315 : std::unique_lock<std::mutex>& reqCtxLock, TpInfo& tpInfo)
316 : {
317 229 : if (reqCtx.tpInfoNum == 0U) {
318 0 : qosMap.erase(it);
319 0 : reqCtxLock.unlock();
320 0 : HCCL_WARNING(
321 : "[TpMgr][%s] failed to find tp info, tpInfoNum is 0, param[%s].", __func__, param.Describe().c_str());
322 0 : return HcclResult::HCCL_E_NOT_FOUND;
323 : }
324 229 : bool isPcieStd = false;
325 229 : CHK_RET(IsPcieStdMainboardByPhyId(devPhyId_, isPcieStd));
326 229 : if (isPcieStd) {
327 0 : const struct HccpTpInfo* list = reinterpret_cast<const struct HccpTpInfo*>(reqCtx.dataBuffer.data());
328 0 : HCCL_INFO(
329 : "[TpMgr][%s] pcie std mainboard: skip GetTpAttr, devPhyId[%u] tpInfoNum[%u] mappedSl[%u] "
330 : "tpHandle[%llu] param[%s].",
331 : __func__, devPhyId_, reqCtx.tpInfoNum, kPcieStdMappedSl, static_cast<unsigned long long>(list[0].tpHandle),
332 : param.Describe().c_str());
333 0 : RequestCtx completedReqCtx = std::move(it->second);
334 0 : qosMap.erase(it);
335 0 : reqCtxLock.unlock();
336 0 : CHK_RET(HandleCompletedRequest(std::move(completedReqCtx), param, tpInfo));
337 0 : return HcclResult::HCCL_SUCCESS;
338 0 : }
339 229 : const struct HccpTpInfo* list = reinterpret_cast<const struct HccpTpInfo*>(reqCtx.dataBuffer.data());
340 229 : HCCL_INFO(
341 : "[TpMgr][GetTpInfo] list stage ok, devPhyId[%u] tpInfoNum[%u] firstTpHandle[%llu] param[%s].", devPhyId_,
342 : reqCtx.tpInfoNum, static_cast<unsigned long long>(list[0].tpHandle), param.Describe().c_str());
343 : try {
344 229 : CHK_RET(StartGetTpAttrForFirstTp(param, reqCtx));
345 0 : } catch (...) {
346 0 : qosMap.erase(it);
347 0 : throw;
348 0 : }
349 229 : HCCL_INFO(
350 : "[TpMgr][GetTpInfo] RaGetTpAttrAsync submitted, devPhyId[%u] reqHandle[%llu] phase[WAIT_TP_ATTR] "
351 : "tpAttrBitmap[0x%x] param[%s].",
352 : devPhyId_, static_cast<unsigned long long>(reqCtx.handle), reqCtx.tpAttrBitmap, param.Describe().c_str());
353 229 : return HcclResult::HCCL_E_AGAIN;
354 : }
355 :
356 : HcclResult
357 687 : TpMgr::PollGetTpInfoReqCtx(std::unique_lock<std::mutex>& reqCtxLock, const GetTpInfoParam& param, TpInfo& tpInfo)
358 : {
359 687 : auto& reqCtxMap = GetReqCtxMap(param.tpProtocol);
360 687 : TpInfoAddrKey key{};
361 687 : CHK_RET(ResolveTpInfoAddrKey(param, key));
362 687 : auto& qosMap = reqCtxMap[key.locAddr][key.rmtAddr];
363 687 : auto it = qosMap.find(key.qosKey);
364 687 : if (it == qosMap.end()) {
365 229 : return BeginGetTpInfoListRequest(param, qosMap, key.qosKey);
366 : }
367 :
368 458 : RequestCtx& reqCtx = it->second;
369 458 : const auto ret = CheckRequestResult(reqCtx.handle);
370 458 : if (ret == HcclResult::HCCL_E_AGAIN) {
371 0 : return ret;
372 : }
373 458 : CHK_RET(ret);
374 :
375 458 : if (reqCtx.phase == ReqPhase::WAIT_LIST) {
376 229 : return AdvanceGetTpInfoWaitList(param, reqCtx, qosMap, it, reqCtxLock, tpInfo);
377 : }
378 :
379 : // 先 move 出槽位再 erase,避免 erase 析构槽内对象后再 move(UB / double free)
380 229 : RequestCtx completedReqCtx = std::move(it->second);
381 229 : qosMap.erase(it);
382 229 : reqCtxLock.unlock();
383 229 : CHK_RET(HandleCompletedRequest(std::move(completedReqCtx), param, tpInfo));
384 229 : return HcclResult::HCCL_SUCCESS;
385 229 : }
386 :
387 692 : HcclResult TpMgr::GetTpInfo(const GetTpInfoParam& param, TpInfo& tpInfo)
388 : {
389 692 : CHK_RET(CheckTpProtocol(param.tpProtocol));
390 691 : if (FindAndGetTpInfo(param, tpInfo) == HcclResult::HCCL_SUCCESS) {
391 4 : return HcclResult::HCCL_SUCCESS;
392 : }
393 :
394 687 : std::unique_lock<std::mutex> reqCtxLock(GetReqCtxMutex(param.tpProtocol));
395 687 : return PollGetTpInfoReqCtx(reqCtxLock, param, tpInfo);
396 687 : }
397 :
398 217 : HcclResult TpMgr::ReleaseTpInfo(const GetTpInfoParam& param, const TpInfo& tpInfo)
399 : {
400 217 : TpInfoAddrKey key{};
401 217 : CHK_RET(ResolveTpInfoAddrKey(param, key));
402 217 : std::lock_guard<std::mutex> lock(GetInfoCtxMutex(param.tpProtocol));
403 217 : auto& infoMap = GetInfoCtxMap(param.tpProtocol);
404 217 : InfoCtxMap::iterator lit;
405 217 : InfoRmtMap::iterator rmtIt;
406 217 : InfoQosMap::iterator qosIt;
407 217 : const auto lookupRet = LookupInfoCtxEntry(infoMap, key.locAddr, key.rmtAddr, key.qosKey, lit, rmtIt, qosIt);
408 217 : if (lookupRet != HcclResult::HCCL_SUCCESS) {
409 7 : if (lit == infoMap.end()) {
410 6 : HCCL_ERROR("[TpMgr][%s] failed, tp info is not found, param[%s].", __func__, param.Describe().c_str());
411 1 : } else if (rmtIt == lit->second.end()) {
412 0 : HCCL_ERROR("[TpMgr][%s] failed, tp info is not found, param[%s].", __func__, param.Describe().c_str());
413 : } else {
414 1 : HCCL_ERROR(
415 : "[TpMgr][%s] failed, tp info is not found for qosKey[%u], param[%s].", __func__,
416 : static_cast<unsigned>(key.qosKey), param.Describe().c_str());
417 : }
418 7 : return HcclResult::HCCL_E_NOT_FOUND;
419 : }
420 :
421 : // 未入缓存的并发 GetTpInfo 结果:与缓存 tpHandle 不一致,无需操作缓存。
422 210 : if (tpInfo.tpHandle != qosIt->second.tpInfo.tpHandle) {
423 1 : return HcclResult::HCCL_SUCCESS;
424 : }
425 :
426 209 : if (qosIt->second.useCnt > 1) {
427 3 : qosIt->second.useCnt -= 1;
428 3 : return HcclResult::HCCL_SUCCESS;
429 : }
430 :
431 206 : rmtIt->second.erase(qosIt);
432 206 : if (rmtIt->second.empty()) {
433 206 : lit->second.erase(rmtIt);
434 : }
435 206 : if (lit->second.empty()) {
436 206 : infoMap.erase(lit);
437 : }
438 206 : return HcclResult::HCCL_SUCCESS;
439 217 : }
440 :
441 229 : static HcclResult GetTpInfoListAsync(
442 : const CtxHandle ctxHandle, const GetTpInfoParam& param, std::vector<char>& out, uint32_t& num,
443 : RequestHandle& reqHandle)
444 : {
445 229 : Hccl::IpAddress locAddr{};
446 229 : Hccl::IpAddress rmtAddr{};
447 229 : CHK_RET(CommAddrToIpAddress(param.locAddr, locAddr));
448 229 : CHK_RET(CommAddrToIpAddress(param.rmtAddr, rmtAddr));
449 229 : const auto& tpProtocol = param.tpProtocol;
450 :
451 229 : struct GetTpCfg cfg {};
452 229 : cfg.flag.bs.rtp = tpProtocol == TpProtocol::RTP ? 1 : 0;
453 229 : cfg.flag.bs.ctp = tpProtocol == TpProtocol::CTP ? 1 : 0;
454 229 : cfg.flag.bs.uboe = tpProtocol == TpProtocol::UBOE ? 1 : 0;
455 229 : cfg.transMode = TransportModeT::CONN_RM;
456 229 : CHK_RET(IpAddressToHccpEid(locAddr, cfg.localEid));
457 229 : HCCL_INFO(
458 : "[TpMgr][GetTpInfoListAsync] cfg.local_eid[subnetPrefix[%016llx], interfaceId[%016llx]]",
459 : static_cast<unsigned long long>(cfg.localEid.in6.subnetPrefix),
460 : static_cast<unsigned long long>(cfg.localEid.in6.interfaceId));
461 229 : CHK_RET(IpAddressToHccpEid(rmtAddr, cfg.peerEid));
462 229 : HCCL_INFO(
463 : "[TpMgr][GetTpInfoListAsync] cfg.peer_eid[subnetPrefix[%016llx], interfaceId[%016llx]]",
464 : static_cast<unsigned long long>(cfg.peerEid.in6.subnetPrefix),
465 : static_cast<unsigned long long>(cfg.peerEid.in6.interfaceId));
466 :
467 : // buffer 须至少容纳本次请求的个数,避免 RS 按 num 写多条 HccpTpInfo 时越界破坏堆
468 229 : out.resize(static_cast<size_t>(Hccl::TP_HANDLE_REQUEST_NUM) * sizeof(struct HccpTpInfo));
469 229 : struct HccpTpInfo* info = reinterpret_cast<struct HccpTpInfo*>(out.data());
470 :
471 229 : void* raReqHandle = nullptr;
472 229 : num = Hccl::TP_HANDLE_REQUEST_NUM; // 指定需要从管控面申请 tp handle 的上限;完成后 num 为实际个数
473 229 : const s32 ret = RaGetTpInfoListAsync(ctxHandle, &cfg, info, &num, &raReqHandle);
474 229 : if (ret != 0 || !raReqHandle) {
475 0 : HCCL_ERROR(
476 : "[TpMgr][%s] failed, call interface error[%d] raReqHandle[%p], ctxHandle[%p] locAddr[%s] rmtAddr[%s].",
477 : __func__, ret, raReqHandle, ctxHandle, locAddr.Describe().c_str(), rmtAddr.Describe().c_str());
478 0 : return HcclResult::HCCL_E_NETWORK;
479 : }
480 :
481 229 : reqHandle = reinterpret_cast<RequestHandle>(raReqHandle);
482 229 : HCCL_INFO("[TpMgr][%s] get request handle[%llu].", __func__, static_cast<unsigned long long>(reqHandle));
483 229 : return HcclResult::HCCL_SUCCESS;
484 : }
485 :
486 229 : HcclResult TpMgr::StartGetTpInfoListRequest(const GetTpInfoParam& param, RequestCtx& reqCtx) const
487 : {
488 : EXCEPTION_HANDLE_BEGIN
489 229 : reqCtx.phase = ReqPhase::WAIT_LIST;
490 229 : reqCtx.tpAttrBitmap = 0;
491 229 : (void)memset_s(&reqCtx.tpAttr, sizeof(reqCtx.tpAttr), 0, sizeof(reqCtx.tpAttr));
492 :
493 229 : Hccl::IpAddress ipAddr{};
494 229 : CHK_RET(CommAddrToIpAddress(param.locAddr, ipAddr));
495 : const CtxHandle ctxHandle
496 229 : = static_cast<CtxHandle>(Hccl::RdmaHandleManager::GetInstance().GetByIp(devPhyId_, ipAddr));
497 229 : CHK_PTR_NULL(ctxHandle);
498 :
499 229 : CHK_RET(GetTpInfoListAsync(ctxHandle, param, reqCtx.dataBuffer, reqCtx.tpInfoNum, reqCtx.handle));
500 0 : EXCEPTION_HANDLE_END
501 229 : return HcclResult::HCCL_SUCCESS;
502 : }
503 :
504 229 : HcclResult TpMgr::StartGetTpAttrForFirstTp(const GetTpInfoParam& param, RequestCtx& reqCtx) const
505 : {
506 229 : EXCEPTION_HANDLE_BEGIN(void) memset_s(&reqCtx.tpAttr, sizeof(reqCtx.tpAttr), 0, sizeof(reqCtx.tpAttr));
507 229 : reqCtx.tpAttrBitmap = (1U << kTpAttrSlAvailableBit) | kTpAttrBitmapSl;
508 229 : if (param.tpProtocol == TpProtocol::UBOE) {
509 10 : reqCtx.tpAttrBitmap |= kTpAttrBitmapDscp | (1U << kTpAttrDscpConfigModeBit);
510 : }
511 :
512 229 : const struct HccpTpInfo* list = reinterpret_cast<const struct HccpTpInfo*>(reqCtx.dataBuffer.data());
513 229 : const uint64_t firstTpHandle = list[0].tpHandle;
514 :
515 229 : Hccl::IpAddress ipAddr{};
516 229 : CHK_RET(CommAddrToIpAddress(param.locAddr, ipAddr));
517 : const CtxHandle ctxHandle
518 229 : = static_cast<CtxHandle>(Hccl::RdmaHandleManager::GetInstance().GetByIp(devPhyId_, ipAddr));
519 229 : CHK_PTR_NULL(ctxHandle);
520 :
521 229 : void* raReqHandle = nullptr;
522 229 : const s32 ret = RaGetTpAttrAsync(ctxHandle, firstTpHandle, &reqCtx.tpAttrBitmap, &reqCtx.tpAttr, &raReqHandle);
523 229 : if (ret != 0 || !raReqHandle) {
524 0 : HCCL_ERROR(
525 : "[TpMgr][%s] RaGetTpAttrAsync failed ret[%d] raReqHandle[%p] ctx[%p] tpHandle[%llu].", __func__, ret,
526 : raReqHandle, ctxHandle, static_cast<unsigned long long>(firstTpHandle));
527 0 : return HcclResult::HCCL_E_NETWORK;
528 : }
529 229 : reqCtx.handle = reinterpret_cast<RequestHandle>(raReqHandle);
530 229 : reqCtx.phase = ReqPhase::WAIT_TP_ATTR;
531 0 : EXCEPTION_HANDLE_END
532 229 : return HcclResult::HCCL_SUCCESS;
533 : }
534 :
535 310 : HcclResult TpMgr::FindAndGetTpAttr(const TpHandle tpHandle, TpAttrInfo& tpAttrInfo)
536 : {
537 310 : std::lock_guard<std::mutex> lock(tpAttrCtxMutex_);
538 310 : auto attrIter = tpAttrCtxMap_.find(tpHandle);
539 310 : if (attrIter != tpAttrCtxMap_.end()) {
540 106 : attrIter->second.useCnt += 1;
541 106 : tpAttrInfo = attrIter->second.tpAttrInfo;
542 106 : return HcclResult::HCCL_SUCCESS;
543 : }
544 :
545 204 : return HcclResult::HCCL_E_NOT_FOUND;
546 310 : }
547 :
548 310 : HcclResult TpMgr::GetTpAttr(const GetTpAttrParam& param, TpAttrInfo& tpAttrInfo, CtxHandle ctxHandle)
549 : {
550 310 : const TpHandle tpHandle = param.tpHandle;
551 310 : if (FindAndGetTpAttr(tpHandle, tpAttrInfo) == HcclResult::HCCL_SUCCESS) {
552 106 : return HcclResult::HCCL_SUCCESS;
553 : }
554 :
555 204 : std::unique_lock<std::mutex> reqCtxLock(tpAttrReqMutex_);
556 204 : auto reqCtxIter = tpAttrReqCtxMap_.find(tpHandle);
557 204 : if (reqCtxIter == tpAttrReqCtxMap_.end()) {
558 102 : HCCL_INFO("[TpMgr][%s] get new tpAttr, param[%s].", __func__, param.Describe().c_str());
559 :
560 102 : TpAttrRequestCtx& reqCtx = tpAttrReqCtxMap_[tpHandle];
561 102 : CHK_RET(StartGetTpAttrRequest(param, reqCtx, ctxHandle));
562 102 : return HcclResult::HCCL_E_AGAIN;
563 : }
564 :
565 102 : auto& reqCtx = reqCtxIter->second;
566 102 : auto ret = CheckRequestResult(reqCtx.handle);
567 102 : if (ret == HcclResult::HCCL_E_AGAIN) {
568 0 : return ret;
569 : }
570 102 : CHK_RET(ret);
571 :
572 102 : TpAttrRequestCtx completedReqCtx = reqCtxIter->second;
573 102 : tpAttrReqCtxMap_.erase(reqCtxIter);
574 102 : reqCtxLock.unlock();
575 102 : CHK_RET(HandleCompletedTpAttrRequest(std::move(completedReqCtx), tpHandle, tpAttrInfo));
576 102 : return HcclResult::HCCL_SUCCESS;
577 204 : }
578 :
579 : HcclResult
580 102 : TpMgr::StartGetTpAttrRequest(const GetTpAttrParam& param, TpMgr::TpAttrRequestCtx& reqCtx, CtxHandle ctxHandle) const
581 : {
582 102 : void* raReqHandle = nullptr;
583 204 : s32 ret = RaGetTpAttrAsync(
584 102 : ctxHandle, param.tpHandle, const_cast<uint32_t*>(¶m.attrBitmap), &reqCtx.tpAttr, &raReqHandle);
585 102 : if (ret != 0 || !raReqHandle) {
586 0 : HCCL_ERROR(
587 : "[TpMgr][%s] failed, call RaGetTpAttrAsync error[%d] raReqHandle[%p], "
588 : "tpHandle[0x%llx] attrBitmap[0x%x].",
589 : __func__, ret, raReqHandle, static_cast<unsigned long long>(param.tpHandle), param.attrBitmap);
590 0 : return HcclResult::HCCL_E_NETWORK;
591 : }
592 :
593 102 : reqCtx.handle = reinterpret_cast<RequestHandle>(raReqHandle);
594 102 : HCCL_INFO(
595 : "[TpMgr][%s] success, tpHandle[0x%llx] reqHandle[%llu].", __func__,
596 : static_cast<unsigned long long>(param.tpHandle), static_cast<unsigned long long>(reqCtx.handle));
597 102 : return HcclResult::HCCL_SUCCESS;
598 : }
599 :
600 102 : HcclResult TpMgr::HandleCompletedTpAttrRequest(
601 : const TpMgr::TpAttrRequestCtx reqCtx, const TpHandle tpHandle, TpAttrInfo& tpAttrInfo)
602 : {
603 102 : TpAttrInfo tmpTpAttrInfo(reqCtx.tpAttr);
604 :
605 102 : std::lock_guard<std::mutex> lock(tpAttrCtxMutex_);
606 102 : tpAttrCtxMap_[tpHandle] = {std::move(tmpTpAttrInfo), 1};
607 :
608 102 : tpAttrInfo = tpAttrCtxMap_[tpHandle].tpAttrInfo;
609 102 : return HcclResult::HCCL_SUCCESS;
610 102 : }
611 :
612 214 : HcclResult TpMgr::ReleaseTpAttr(const TpHandle tpHandle, [[maybe_unused]] const TpAttrInfo& tpAttrInfo)
613 : {
614 214 : std::lock_guard<std::mutex> lock(tpAttrCtxMutex_);
615 214 : auto attrIter = tpAttrCtxMap_.find(tpHandle);
616 214 : if (attrIter == tpAttrCtxMap_.end()) {
617 7 : HCCL_ERROR(
618 : "[TpMgr][%s] failed, tp attr is not found, "
619 : "tpHandle[0x%llx].",
620 : __func__, static_cast<unsigned long long>(tpHandle));
621 7 : return HcclResult::HCCL_E_NOT_FOUND;
622 : }
623 :
624 207 : if (attrIter->second.useCnt > 1) {
625 106 : attrIter->second.useCnt -= 1;
626 106 : return HcclResult::HCCL_SUCCESS;
627 : }
628 :
629 101 : tpAttrCtxMap_.erase(attrIter);
630 101 : return HcclResult::HCCL_SUCCESS;
631 214 : }
632 :
633 211 : HcclResult TpMgr::GetTpTotalTimeout(const TpAttrInfo& tpAttrInfo, uint32_t& tpTimeOutMs)
634 : {
635 211 : uint8_t rawAtGear = tpAttrInfo.tpAttr.at;
636 211 : uint8_t rawRetryTimes = tpAttrInfo.tpAttr.retryTimesInit;
637 :
638 211 : uint8_t finalAtGear = rawAtGear;
639 211 : if (rawAtGear > AT_GEAR_MAX) {
640 1 : finalAtGear = AT_GEAR_DEFAULT;
641 1 : HCCL_WARNING(
642 : "[TpMgr][%s] Invalid at gear[%u], expect [%u, %u], use default gear[%u].", __func__,
643 : static_cast<unsigned>(rawAtGear), static_cast<unsigned>(AT_GEAR_MIN), static_cast<unsigned>(AT_GEAR_MAX),
644 : static_cast<unsigned>(finalAtGear));
645 : }
646 :
647 211 : uint32_t singleAtTimeoutMs = AT_TIMEOUT_MAP[finalAtGear];
648 211 : tpTimeOutMs = singleAtTimeoutMs * static_cast<uint32_t>(rawRetryTimes + 1);
649 :
650 211 : HCCL_INFO(
651 : "[TpMgr][%s] TP timeout calc success: raw_at_gear[%u], final_at_gear[%u], "
652 : "single_timeout[%ums], retry_times[%u], total_timeout[%ums].",
653 : __func__, static_cast<unsigned>(rawAtGear), static_cast<unsigned>(finalAtGear), singleAtTimeoutMs,
654 : static_cast<unsigned>(rawRetryTimes), tpTimeOutMs);
655 :
656 211 : return HcclResult::HCCL_SUCCESS;
657 : }
658 :
659 209 : static uint32_t TaHwValueToMs(uint8_t hwValue)
660 : {
661 209 : uint8_t gear = hwValue / 8;
662 209 : switch (gear) {
663 1 : case TA_GEAR_INDEX_0:
664 1 : return TA_TIMEOUT_MS_GEAR0;
665 0 : case TA_GEAR_INDEX_1:
666 0 : return TA_TIMEOUT_MS_GEAR1;
667 207 : case TA_GEAR_INDEX_2:
668 207 : return TA_TIMEOUT_MS_GEAR2;
669 1 : case TA_GEAR_INDEX_3:
670 1 : return TA_TIMEOUT_MS_GEAR3;
671 0 : default:
672 0 : return TA_TIMEOUT_MS_GEAR2;
673 : }
674 : }
675 :
676 1 : static uint8_t FindMinTaHwValue(uint32_t tpTotalTimeoutMs)
677 : {
678 1 : if (tpTotalTimeoutMs < TA_TIMEOUT_MS_GEAR0) {
679 0 : return TA_HW_GEAR0_BASE;
680 : }
681 1 : if (tpTotalTimeoutMs < TA_TIMEOUT_MS_GEAR1) {
682 0 : return TA_HW_GEAR1_BASE;
683 : }
684 1 : if (tpTotalTimeoutMs < TA_TIMEOUT_MS_GEAR2) {
685 1 : return TA_HW_GEAR2_BASE;
686 : }
687 0 : return TA_HW_GEAR3_BASE;
688 : }
689 :
690 208 : uint8_t TpMgr::CalcTaTimeout(TpProtocol tpProtocol, uint8_t taTimeOut, uint32_t tpTimeOutMs)
691 : {
692 : // 未传入时回退到协议默认值(CTP=8,其他=16)
693 208 : uint8_t envValue = (taTimeOut != TA_TIMEOUT_NOT_SET) ? taTimeOut : ((tpProtocol == TpProtocol::CTP) ? 8 : 16);
694 208 : uint32_t envTimeOutMs = TaHwValueToMs(envValue);
695 :
696 : // CTP 协议直接使用 envValue,不与 TP 总超时比较
697 208 : if (tpProtocol == TpProtocol::CTP) {
698 0 : HCCL_INFO("[TpMgr][%s] [UbCtp] Env Value [%u] (%ums).", __func__, envValue, envTimeOutMs);
699 0 : return envValue;
700 : }
701 :
702 : // 其他协议:需要与 TP 总超时比较决定是否自动升挡
703 208 : uint8_t jettyTimeOut = envValue;
704 208 : if (envTimeOutMs <= tpTimeOutMs) {
705 1 : jettyTimeOut = FindMinTaHwValue(tpTimeOutMs);
706 1 : HCCL_WARNING(
707 : "[TpMgr][%s] Env timeout [%ums] <= TP timeout [%ums]. Auto upgrade TA to hw_val[%u] (%ums).", __func__,
708 : envTimeOutMs, tpTimeOutMs, jettyTimeOut, TaHwValueToMs(jettyTimeOut));
709 : } else {
710 207 : HCCL_INFO(
711 : "[TpMgr][%s] Env timeout [%ums] > TP timeout [%ums]. Use env gear base hw_val[%u] (%ums).", __func__,
712 : envTimeOutMs, tpTimeOutMs, envValue, envTimeOutMs);
713 : }
714 :
715 208 : return jettyTimeOut;
716 : }
717 :
718 229 : HcclResult TpMgr::BuildTpInfoAndCommitQosAttr(
719 : const GetTpInfoParam& param, const RequestCtx& reqCtx, const struct HccpTpInfo* baseInfoPtr,
720 : const uint32_t tpListIndex, const uint32_t mappedSl, TpInfo& tpInfo)
721 : {
722 229 : tpInfo = TpInfo{};
723 229 : tpInfo.tpHandle = baseInfoPtr[tpListIndex].tpHandle;
724 229 : tpInfo.mappedJettyPriority = mappedSl & 0xFU;
725 229 : tpInfo.hasMappedJettyPriority = true;
726 :
727 229 : bool isPcieStd = false;
728 229 : CHK_RET(IsPcieStdMainboardByPhyId(devPhyId_, isPcieStd));
729 229 : if (isPcieStd) {
730 0 : HCCL_INFO(
731 : "[TpMgr][%s] pcie std mainboard: skip SetTpAttr, devPhyId[%u] tpProtocol[%s] tpHandle[%llu] "
732 : "param[%s].",
733 : __func__, devPhyId_, param.tpProtocol.Describe().c_str(), static_cast<unsigned long long>(tpInfo.tpHandle),
734 : param.Describe().c_str());
735 229 : } else if (param.tpProtocol == TpProtocol::RTP || param.tpProtocol == TpProtocol::UBOE) {
736 225 : CHK_RET(CommitMappedSlToTpAttr(devPhyId_, param.locAddr, tpInfo.tpHandle, mappedSl));
737 : }
738 229 : if (!isPcieStd && param.tpProtocol == TpProtocol::UBOE && reqCtx.tpAttr.dscpConfigMode == 0) {
739 7 : const uint8_t dscpBefore = static_cast<uint8_t>(reqCtx.tpAttr.dscp & 0x3FU);
740 7 : const uint8_t requestQos = static_cast<uint8_t>(param.qos & 0xFFU);
741 7 : const uint16_t slMask = ReadSlAvailableMask16(reqCtx.tpAttr);
742 7 : const uint8_t dscpLookupQos = ResolveUboeDscpLookupQos(param, reqCtx.tpInfoNum, slMask);
743 7 : uint8_t dscp = Hccl::kUboeDefaultDscp;
744 7 : (void)Hccl::TpQosGetDscpByQosFromHccnCfg(devPhyId_, dscpLookupQos, dscp);
745 7 : CHK_RET(CommitUboeDscpToTpAttr(devPhyId_, param.locAddr, tpInfo.tpHandle, dscp));
746 7 : HCCL_INFO(
747 : "[TpMgr][%s] UBOE dscp updated: tpHandle[%llu] requestQos[%u] dscpLookupQos[%u] dscpBefore[%u] "
748 : "dscpAfter[%u].",
749 : __func__, static_cast<unsigned long long>(tpInfo.tpHandle), static_cast<unsigned>(requestQos),
750 : static_cast<unsigned>(dscpLookupQos), static_cast<unsigned>(dscpBefore), static_cast<unsigned>(dscp));
751 : }
752 229 : HCCL_INFO(
753 : "[TpMgr][%s] tp qos mapping ok: tpHandle[%llu] tpListIndex[%u] mappedSl[%u] jettyPriority[%u] qos[%u] "
754 : "param[%s].",
755 : __func__, static_cast<unsigned long long>(tpInfo.tpHandle), tpListIndex, static_cast<unsigned>(mappedSl & 0xFU),
756 : tpInfo.mappedJettyPriority, param.qos & 0xFFU, param.Describe().c_str());
757 229 : return HcclResult::HCCL_SUCCESS;
758 : }
759 :
760 : // GetTpInfo 完成后写入缓存。useCnt 仅在 FindAndGetTpInfo 命中时 +1,此处不做引用计数。
761 : // 并发首次 GetTpInfo 时,先完成者写入缓存;后完成者若 tpHandle 不同则跳过写入,直接使用本地结果。
762 229 : HcclResult TpMgr::CommitTpInfoToCache(const GetTpInfoParam& param, TpInfo& tpInfo)
763 : {
764 229 : Hccl::IpAddress locAddr{};
765 229 : Hccl::IpAddress rmtAddr{};
766 229 : CHK_RET(CommAddrToIpAddress(param.locAddr, locAddr));
767 229 : CHK_RET(CommAddrToIpAddress(param.rmtAddr, rmtAddr));
768 229 : const QosKey qosKey = QosMapKey(param.qos);
769 :
770 229 : std::lock_guard<std::mutex> lock(GetInfoCtxMutex(param.tpProtocol));
771 229 : auto& infoMap = GetInfoCtxMap(param.tpProtocol);
772 229 : auto& rmtMap = infoMap[locAddr][rmtAddr];
773 229 : const auto qIt = rmtMap.find(qosKey);
774 229 : if (qIt == rmtMap.end()) {
775 229 : rmtMap[qosKey] = TpInfoCtx{tpInfo, 1U};
776 229 : return HcclResult::HCCL_SUCCESS;
777 : }
778 :
779 : // 缓存已存在:不再覆盖(避免并发后写覆盖先写的 tpHandle);tpInfo 保持 GetTpInfo 本地结果。
780 0 : if (qIt->second.tpInfo.tpHandle != tpInfo.tpHandle) {
781 0 : HCCL_WARNING(
782 : "[TpMgr][%s] skip cache store, cached tpHandle[%llu] != local tpHandle[%llu] param[%s].", __func__,
783 : static_cast<unsigned long long>(qIt->second.tpInfo.tpHandle),
784 : static_cast<unsigned long long>(tpInfo.tpHandle), param.Describe().c_str());
785 : }
786 0 : return HcclResult::HCCL_SUCCESS;
787 229 : }
788 :
789 229 : HcclResult TpMgr::HandleCompletedRequest(RequestCtx reqCtx, const GetTpInfoParam& param, TpInfo& tpInfo)
790 : {
791 229 : const uint32_t tpInfoNum = reqCtx.tpInfoNum;
792 229 : if (tpInfoNum == 0U) {
793 0 : HCCL_WARNING(
794 : "[TpMgr][%s] failed to find tp info, tpInfoNum is 0, param[%s].", __func__, param.Describe().c_str());
795 0 : return HcclResult::HCCL_E_NOT_FOUND;
796 : }
797 :
798 229 : tpInfo = TpInfo{};
799 :
800 229 : const struct HccpTpInfo* baseInfoPtr = reinterpret_cast<const struct HccpTpInfo*>(reqCtx.dataBuffer.data());
801 229 : bool isPcieStd = false;
802 229 : CHK_RET(IsPcieStdMainboardByPhyId(devPhyId_, isPcieStd));
803 229 : if (isPcieStd) {
804 0 : tpInfo.tpHandle = baseInfoPtr[0].tpHandle;
805 0 : tpInfo.mappedJettyPriority = kPcieStdMappedSl;
806 0 : tpInfo.hasMappedJettyPriority = true;
807 0 : HCCL_INFO(
808 : "[TpMgr][%s] pcie std mainboard: skip GetTpAttr/SetTpAttr, devPhyId[%u] tpInfoNum[%u] "
809 : "mappedSl[%u] tpHandle[%llu] param[%s].",
810 : __func__, devPhyId_, tpInfoNum, kPcieStdMappedSl, static_cast<unsigned long long>(tpInfo.tpHandle),
811 : param.Describe().c_str());
812 0 : return CommitTpInfoToCache(param, tpInfo);
813 : }
814 :
815 229 : const uint16_t slMask = ReadSlAvailableMask16(reqCtx.tpAttr);
816 229 : const uint32_t slAvailableCnt = CalSlAvailableCnt(slMask);
817 229 : HCCL_INFO(
818 : "[TpMgr][%s] after get_tp_attr: slMask[0x%04x] slAvailableCnt[%u] slBitmap[0x%x] dscp[%u] dscpConfigMode[%u] "
819 : "tpAttrBitmap[0x%x] param[%s].",
820 : __func__, static_cast<unsigned>(slMask), slAvailableCnt, static_cast<unsigned>(reqCtx.tpAttr.slBitmap),
821 : static_cast<unsigned>(reqCtx.tpAttr.dscp & 0x3FU), static_cast<unsigned>(reqCtx.tpAttr.dscpConfigMode & 1U),
822 : reqCtx.tpAttrBitmap, param.Describe().c_str());
823 229 : if (slAvailableCnt == 0U) {
824 0 : HCCL_ERROR(
825 : "[TpMgr][%s] sl_available mask empty after get_tp_attr, param[%s].", __func__, param.Describe().c_str());
826 0 : return HcclResult::HCCL_E_INTERNAL;
827 : }
828 229 : uint32_t tpListIndex = 0;
829 229 : uint32_t mappedSl = 0;
830 229 : if (!ApplyQosTpSlPolicy(param, slMask, tpListIndex, mappedSl)) {
831 0 : HCCL_ERROR(
832 : "[TpMgr][%s] ApplyQosTpSlPolicy failed, param[%s] nTp[%u] slAvailableCnt[%u] mask[%u].", __func__,
833 : param.Describe().c_str(), tpInfoNum, slAvailableCnt, static_cast<unsigned>(slMask));
834 0 : return HcclResult::HCCL_E_INTERNAL;
835 : }
836 229 : if (tpListIndex >= tpInfoNum) {
837 0 : HCCL_ERROR(
838 : "[TpMgr][%s] tpListIndex out of range: tpListIndex[%u] tpInfoNum[%u] mappedSl[%u] param[%s].", __func__,
839 : tpListIndex, tpInfoNum, static_cast<unsigned>(mappedSl & 0xFU), param.Describe().c_str());
840 0 : return HcclResult::HCCL_E_INTERNAL;
841 : }
842 :
843 229 : CHK_RET(BuildTpInfoAndCommitQosAttr(param, reqCtx, baseInfoPtr, tpListIndex, mappedSl, tpInfo));
844 229 : return CommitTpInfoToCache(param, tpInfo);
845 : }
846 :
847 1137 : TpMgr::InfoCtxMap& TpMgr::GetInfoCtxMap(const TpProtocol tpProtocol)
848 : {
849 1137 : switch (tpProtocol) {
850 16 : case TpProtocol::CTP:
851 16 : return ctpInfoMap_;
852 1081 : case TpProtocol::RTP:
853 1081 : return rtpInfoMap_;
854 40 : case TpProtocol::UBOE:
855 40 : return uboeInfoMap_;
856 0 : default:
857 0 : return rtpInfoMap_;
858 : }
859 : }
860 :
861 687 : TpMgr::ReqCtxMap& TpMgr::GetReqCtxMap(const TpProtocol tpProtocol)
862 : {
863 687 : switch (tpProtocol) {
864 12 : case TpProtocol::CTP:
865 12 : return ctpReqMap_;
866 645 : case TpProtocol::RTP:
867 645 : return rtpReqMap_;
868 30 : case TpProtocol::UBOE:
869 30 : return uboeReqMap_;
870 0 : default:
871 0 : return rtpReqMap_;
872 : }
873 : }
874 :
875 1137 : std::mutex& TpMgr::GetInfoCtxMutex(const TpProtocol tpProtocol)
876 : {
877 1137 : switch (tpProtocol) {
878 16 : case TpProtocol::CTP:
879 16 : return ctpInfoMutex_;
880 1081 : case TpProtocol::RTP:
881 1081 : return rtpInfoMutex_;
882 40 : case TpProtocol::UBOE:
883 40 : return uboeInfoMutex_;
884 0 : default:
885 0 : return rtpInfoMutex_;
886 : }
887 : }
888 :
889 687 : std::mutex& TpMgr::GetReqCtxMutex(const TpProtocol tpProtocol)
890 : {
891 687 : switch (tpProtocol) {
892 12 : case TpProtocol::CTP:
893 12 : return ctpReqMutex_;
894 645 : case TpProtocol::RTP:
895 645 : return rtpReqMutex_;
896 30 : case TpProtocol::UBOE:
897 30 : return uboeReqMutex_;
898 0 : default:
899 0 : return rtpReqMutex_;
900 : }
901 : }
902 :
903 : } // namespace hcomm
|