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 : #include "typical_qp_manager.h"
11 : #include <map>
12 : #include <memory>
13 : #include "externalinput.h"
14 : #include "adapter_rts_common.h"
15 : #include "rdma_resource_manager.h"
16 :
17 : namespace hccl {
18 66 : TypicalQpManager::TypicalQpManager() {}
19 :
20 66 : TypicalQpManager::~TypicalQpManager()
21 : {
22 66 : std::unique_lock<std::mutex> cqLock(cqMutex_);
23 66 : for (auto& item : cqMap_) {
24 0 : if (item.second.second == nullptr) {
25 0 : continue;
26 : }
27 0 : DestroyTypicalCq(rdmaHandle_, item.first, item.second.second);
28 : }
29 66 : cqMap_.clear();
30 66 : cqLock.unlock();
31 :
32 66 : std::unique_lock<std::mutex> lock(qpMutex_);
33 72 : for (auto& item : qpMap_) {
34 6 : if (item.second.second == nullptr) {
35 0 : continue;
36 : }
37 6 : HrtRaQpDestroy(item.second.second);
38 : }
39 66 : qpMap_.clear();
40 66 : for (auto& item : verbsQpMap_) {
41 0 : if (item.second.second == nullptr) {
42 0 : continue;
43 : }
44 0 : HrtRaQpDestroyWithoutCQ(item.second.second);
45 : }
46 66 : verbsQpMap_.clear();
47 66 : lock.unlock();
48 66 : }
49 :
50 209 : TypicalQpManager& TypicalQpManager::GetInstance()
51 : {
52 275 : static TypicalQpManager qpInstance[MAX_MODULE_DEVICE_NUM + 1];
53 209 : s32 deviceLogicId = INVALID_INT;
54 209 : HcclResult ret = hrtGetDevice(&deviceLogicId);
55 209 : if (ret == HCCL_SUCCESS && (static_cast<u32>(deviceLogicId) < MAX_MODULE_DEVICE_NUM)) {
56 209 : HCCL_INFO("[TypicalQpManager::GetInstance]deviceLogicID[%d]", deviceLogicId);
57 209 : return qpInstance[deviceLogicId];
58 : }
59 0 : HCCL_WARNING("[TypicalQpManager::GetInstance]deviceLogicID[%d] is invalid, ret[%d]", deviceLogicId, ret);
60 0 : return qpInstance[MAX_MODULE_DEVICE_NUM];
61 : }
62 :
63 30 : HcclResult TypicalQpManager::CreateQp(struct TypicalQp& qpInfo)
64 : {
65 30 : HcclResult ret = HCCL_SUCCESS;
66 30 : QpHandle qpHandle = nullptr;
67 30 : CHK_RET(RdmaResourceManager::GetInstance().GetRdmaHandle(rdmaHandle_));
68 30 : CHK_PTR_NULL(rdmaHandle_);
69 30 : std::unique_lock<std::mutex> lock(qpMutex_);
70 30 : ret = hrtRaTypicalQpCreate(rdmaHandle_, QP_FLAG_RC, OPBASE_QP_MODE, &qpInfo, qpHandle);
71 30 : CHK_PRT_RET(ret != HCCL_SUCCESS, HCCL_ERROR("[TypicalQpManager][CreateQp] Create qp failed."), HCCL_E_INTERNAL);
72 30 : qpMap_.insert(std::make_pair(qpInfo.qpn, std::make_pair(qpInfo, qpHandle)));
73 30 : return HCCL_SUCCESS;
74 30 : }
75 :
76 10 : HcclResult TypicalQpManager::CreateQp(struct TypicalQp& qpInfo, const QpConfigInfo& qpConfig)
77 : {
78 10 : HcclResult ret = HCCL_SUCCESS;
79 10 : QpHandle qpHandle = nullptr;
80 10 : CHK_RET(RdmaResourceManager::GetInstance().GetRdmaHandle(rdmaHandle_));
81 10 : CHK_PTR_NULL(rdmaHandle_);
82 10 : std::unique_lock<std::mutex> lock(qpMutex_);
83 10 : ret = CreateQpWithDepthConfig(rdmaHandle_, OPBASE_QP_MODE, qpConfig, qpHandle, qpInfo);
84 10 : CHK_PRT_RET(ret != HCCL_SUCCESS, HCCL_ERROR("[TypicalQpManager][CreateQp] Create qp failed."), HCCL_E_INTERNAL);
85 9 : qpMap_.insert(std::make_pair(qpInfo.qpn, std::make_pair(qpInfo, qpHandle)));
86 9 : return HCCL_SUCCESS;
87 10 : }
88 :
89 1 : HcclResult TypicalQpManager::CreateCq(AscendCQInfo& cqInfo)
90 : {
91 1 : HcclResult ret = HCCL_SUCCESS;
92 1 : void* cqHandle = nullptr;
93 1 : CHK_RET(RdmaResourceManager::GetInstance().GetRdmaHandle(rdmaHandle_));
94 1 : CHK_PTR_NULL(rdmaHandle_);
95 1 : std::unique_lock<std::mutex> lock(cqMutex_);
96 1 : ret = CreateTypicalCq(rdmaHandle_, cqInfo.cqDepth, cqInfo.cqn, &cqHandle);
97 1 : CHK_PRT_RET(ret != HCCL_SUCCESS, HCCL_ERROR("[TypicalQpManager][CreateCq] Create cq failed."), HCCL_E_INTERNAL);
98 1 : cqMap_.insert(std::make_pair(cqInfo.cqn, std::make_pair(cqInfo, cqHandle)));
99 1 : return HCCL_SUCCESS;
100 1 : }
101 :
102 0 : HcclResult TypicalQpManager::DestroyCq(uint32_t cqn)
103 : {
104 0 : HcclResult ret = HCCL_SUCCESS;
105 0 : CHK_RET(RdmaResourceManager::GetInstance().GetRdmaHandle(rdmaHandle_));
106 0 : CHK_PTR_NULL(rdmaHandle_);
107 0 : std::unique_lock<std::mutex> lock(cqMutex_);
108 0 : auto it = cqMap_.find(cqn);
109 0 : CHK_PRT_RET((it == cqMap_.end()), HCCL_ERROR("[TypicalQpManager][DestroyCq] cqn[%u] not found.", cqn), HCCL_E_PARA);
110 0 : ret = DestroyTypicalCq(rdmaHandle_, cqn, it->second.second);
111 0 : CHK_PRT_RET(ret != HCCL_SUCCESS, HCCL_ERROR("[TypicalQpManager][DestroyCq] Destroy cq failed."), HCCL_E_INTERNAL);
112 0 : cqMap_.erase(it);
113 0 : return HCCL_SUCCESS;
114 0 : }
115 :
116 0 : HcclResult TypicalQpManager::ValidateCq(uint32_t cqn)
117 : {
118 0 : std::unique_lock<std::mutex> lock(cqMutex_);
119 0 : auto it = cqMap_.find(cqn);
120 0 : CHK_PRT_RET(
121 : (it == cqMap_.end()), HCCL_ERROR("[TypicalQpManager][ValidateCq] cqn[%u] not found.", cqn), HCCL_E_PARA);
122 0 : return HCCL_SUCCESS;
123 0 : }
124 :
125 0 : HcclResult TypicalQpManager::GetCqDepth(uint32_t cqn, uint32_t& cqDepth)
126 : {
127 0 : std::unique_lock<std::mutex> lock(cqMutex_);
128 0 : auto it = cqMap_.find(cqn);
129 0 : CHK_PRT_RET(
130 : (it == cqMap_.end()), HCCL_ERROR("[TypicalQpManager][GetCqDepth] cqn[%u] not found.", cqn), HCCL_E_PARA);
131 0 : cqDepth = it->second.first.cqDepth;
132 0 : return HCCL_SUCCESS;
133 0 : }
134 :
135 0 : HcclResult TypicalQpManager::GetCqHandle(uint32_t cqn, void*& cqHandle)
136 : {
137 0 : std::unique_lock<std::mutex> lock(cqMutex_);
138 0 : auto it = cqMap_.find(cqn);
139 0 : CHK_PRT_RET(
140 : (it == cqMap_.end()), HCCL_ERROR("[TypicalQpManager][GetCqHandle] cqn[%u] not found.", cqn), HCCL_E_PARA);
141 0 : cqHandle = it->second.second;
142 0 : return HCCL_SUCCESS;
143 0 : }
144 :
145 2 : HcclResult TypicalQpManager::CreateQpWithCQ(struct TypicalQp& qpInfo, const QpConfigWithCQInfo& qpConfig)
146 : {
147 2 : HcclResult ret = HCCL_SUCCESS;
148 2 : QpHandle qpHandle = nullptr;
149 2 : CHK_RET(RdmaResourceManager::GetInstance().GetRdmaHandle(rdmaHandle_));
150 2 : CHK_PTR_NULL(rdmaHandle_);
151 2 : std::unique_lock<std::mutex> lock(qpMutex_);
152 2 : ret = CreateQpWithCQConfig(rdmaHandle_, OPBASE_QP_MODE, qpConfig, qpHandle, qpInfo);
153 2 : CHK_PRT_RET(
154 : ret != HCCL_SUCCESS, HCCL_ERROR("[TypicalQpManager][CreateQpWithCQ] Create qp with cq failed."),
155 : HCCL_E_INTERNAL);
156 1 : verbsQpMap_.insert(std::make_pair(qpInfo.qpn, std::make_pair(qpInfo, qpHandle)));
157 1 : return HCCL_SUCCESS;
158 2 : }
159 :
160 30 : HcclResult TypicalQpManager::ModifyQp(struct TypicalQp& localQpInfo, struct TypicalQp& remoteQpInfo)
161 : {
162 30 : CHK_PRT_RET(
163 : (localQpInfo.qpn == 0 || remoteQpInfo.qpn == 0),
164 : HCCL_ERROR("[TypicalQpManager][ModifyQp] the qpinfo is wrong, qpn is 0."), HCCL_E_PARA);
165 30 : QpHandle qpHandle = nullptr;
166 30 : CHK_RET(GetQpHandleByQpn(localQpInfo.qpn, qpHandle));
167 30 : CHK_PTR_NULL(qpHandle);
168 30 : CHK_RET(SetQpRdmaRetryCfg(localQpInfo));
169 30 : std::unique_lock<std::mutex> lock(qpMutex_);
170 30 : HcclResult ret = hrtRaTypicalQpModify(qpHandle, &localQpInfo, &remoteQpInfo);
171 30 : CHK_PRT_RET(ret != HCCL_SUCCESS, HCCL_ERROR("[TypicalQpManager][ModifyQp] Modify qp failed."), HCCL_E_INTERNAL);
172 :
173 30 : return HCCL_SUCCESS;
174 30 : }
175 :
176 5 : HcclResult TypicalQpManager::ModifyVerbsQp(struct TypicalQp& localQpInfo, struct TypicalQp& remoteQpInfo)
177 : {
178 5 : CHK_PRT_RET(
179 : (localQpInfo.qpn == 0 || remoteQpInfo.qpn == 0),
180 : HCCL_ERROR("[TypicalQpManager][ModifyVerbsQp] the qpinfo is wrong, qpn is 0."), HCCL_E_PARA);
181 3 : QpHandle qpHandle = nullptr;
182 3 : CHK_RET(GetVerbsQpHandleByQpn(localQpInfo.qpn, qpHandle));
183 2 : CHK_PTR_NULL(qpHandle);
184 2 : CHK_RET(SetQpRdmaRetryCfg(localQpInfo));
185 2 : std::unique_lock<std::mutex> lock(qpMutex_);
186 2 : HcclResult ret = hrtRaTypicalQpModify(qpHandle, &localQpInfo, &remoteQpInfo);
187 2 : CHK_PRT_RET(
188 : ret != HCCL_SUCCESS, HCCL_ERROR("[TypicalQpManager][ModifyVerbsQp] Modify qp failed."), HCCL_E_INTERNAL);
189 :
190 1 : return HCCL_SUCCESS;
191 2 : }
192 :
193 30 : HcclResult TypicalQpManager::DestroyQp(struct TypicalQp& qpInfo)
194 : {
195 30 : CHK_PRT_RET(
196 : (qpInfo.qpn == 0), HCCL_ERROR("[TypicalQpManager][DestroyQp] The qpinfo is wrong, qpn is 0."), HCCL_E_PARA);
197 : QpHandle qpHandle;
198 30 : CHK_RET(GetQpHandleByQpn(qpInfo.qpn, qpHandle));
199 30 : CHK_PTR_NULL(qpHandle);
200 30 : std::unique_lock<std::mutex> lock(qpMutex_);
201 30 : HcclResult ret = HrtRaQpDestroy(qpHandle);
202 30 : CHK_PRT_RET(ret != HCCL_SUCCESS, HCCL_ERROR("[TypicalQpManager][DestroyQp] Destroy qp failed."), HCCL_E_INTERNAL);
203 30 : qpMap_.erase(qpInfo.qpn);
204 30 : return HCCL_SUCCESS;
205 30 : }
206 :
207 4 : HcclResult TypicalQpManager::DestroyQpWithoutCQ(struct TypicalQp& qpInfo)
208 : {
209 4 : CHK_PRT_RET(
210 : (qpInfo.qpn == 0), HCCL_ERROR("[TypicalQpManager][DestroyQpWithoutCQ] The qpinfo is wrong, qpn is 0."),
211 : HCCL_E_PARA);
212 : QpHandle qpHandle;
213 3 : CHK_RET(GetVerbsQpHandleByQpn(qpInfo.qpn, qpHandle));
214 2 : CHK_PTR_NULL(qpHandle);
215 2 : std::unique_lock<std::mutex> lock(qpMutex_);
216 2 : HcclResult ret = HrtRaQpDestroyWithoutCQ(qpHandle);
217 2 : CHK_PRT_RET(
218 : ret != HCCL_SUCCESS, HCCL_ERROR("[TypicalQpManager][DestroyQpWithoutCQ] Destroy qp without cq failed."),
219 : HCCL_E_INTERNAL);
220 1 : verbsQpMap_.erase(qpInfo.qpn);
221 1 : return HCCL_SUCCESS;
222 2 : }
223 :
224 32 : HcclResult TypicalQpManager::SetQpRdmaRetryCfg(struct TypicalQp& qpInfo)
225 : {
226 32 : qpInfo.retryCnt = GetExternalInputRdmaRetryCnt();
227 32 : qpInfo.retryTime = GetExternalInputRdmaTimeOut();
228 32 : HCCL_INFO(
229 : "[TypicalQpManager][SetQpCreateBaseInfo] Qpinfo is set, tc is %u, sl is %u, retry cnt is %u, "
230 : "retry time is %u",
231 : qpInfo.tc, qpInfo.sl, qpInfo.retryCnt, qpInfo.retryTime);
232 32 : return HCCL_SUCCESS;
233 : }
234 :
235 108 : HcclResult TypicalQpManager::GetQpHandleByQpn(u32 qpn, QpHandle& qpHandle)
236 : {
237 108 : HCCL_DEBUG("[TypicalQpManager][GetQpHandleByQpn] Get qpHandle by qpn[%u]", qpn);
238 108 : CHK_RET(RdmaResourceManager::GetInstance().GetRdmaHandle(rdmaHandle_));
239 108 : CHK_PTR_NULL(rdmaHandle_);
240 108 : std::unique_lock<std::mutex> lock(qpMutex_);
241 108 : auto it = qpMap_.find(qpn);
242 108 : CHK_PRT_RET(
243 : (it == qpMap_.end()), HCCL_ERROR("[TypicalQpManager][GetQpHandleByQpn] Qpn is not found"), HCCL_E_NOT_FOUND);
244 108 : qpHandle = it->second.second;
245 108 : CHK_PRT_RET(
246 : (qpHandle == nullptr),
247 : HCCL_ERROR("[TypicalQpManager][GetQpHandleByQpn] Get Qphandle failed, qphandle is nullptr. qpn is %u", qpn),
248 : HCCL_E_NOT_FOUND);
249 108 : return HCCL_SUCCESS;
250 108 : }
251 :
252 10 : HcclResult TypicalQpManager::GetVerbsQpHandleByQpn(u32 qpn, QpHandle& qpHandle)
253 : {
254 10 : HCCL_DEBUG("[TypicalQpManager][GetVerbsQpHandleByQpn] Get qpHandle by qpn[%u]", qpn);
255 10 : CHK_RET(RdmaResourceManager::GetInstance().GetRdmaHandle(rdmaHandle_));
256 9 : CHK_PTR_NULL(rdmaHandle_);
257 9 : std::unique_lock<std::mutex> lock(qpMutex_);
258 9 : auto it = verbsQpMap_.find(qpn);
259 9 : CHK_PRT_RET(
260 : (it == verbsQpMap_.end()), HCCL_ERROR("[TypicalQpManager][GetVerbsQpHandleByQpn] Qpn is not found"),
261 : HCCL_E_NOT_FOUND);
262 6 : qpHandle = it->second.second;
263 6 : CHK_PRT_RET(
264 : (qpHandle == nullptr),
265 : HCCL_ERROR(
266 : "[TypicalQpManager][GetVerbsQpHandleByQpn] Get Qphandle failed, qphandle is nullptr. qpn is %u", qpn),
267 : HCCL_E_NOT_FOUND);
268 5 : return HCCL_SUCCESS;
269 9 : }
270 : } // namespace hccl
|