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 "aicpu_channel_process.h"
12 : #include "dev_aicpu_ts_channel_mgr.h"
13 : #include "aicpu_res_package_helper.h"
14 : #include "../channel.h"
15 : #include "aicpu_ts_channel_helper.h"
16 :
17 : #include "adapter_rts_common.h"
18 : #include "log.h"
19 :
20 : #include <securec.h>
21 :
22 : #include <cstdint>
23 : #include <vector>
24 :
25 : std::mutex AicpuChannelProcess::mutex_;
26 : std::unordered_map<ChannelHandle, std::unique_ptr<Hccl::UbTransportLiteImpl>>
27 : AicpuChannelProcess::ubTransportMap_;
28 :
29 0 : HcclResult AicpuChannelProcess::ParsePackData(std::vector<char> &data, ChannelHandle &handle)
30 : {
31 0 : HCCL_DEBUG("[HcclCommAicpu][%s] data: ptr[%p], size[%u]", __func__, data.data(), data.size());
32 0 : Hccl::BinaryStream binaryStream(data);
33 :
34 0 : std::vector<char> transpUniqueId;
35 0 : binaryStream >> transpUniqueId;
36 :
37 0 : Hccl::BinaryStream binaryStreamForType(transpUniqueId);
38 : u32 transType;
39 0 : binaryStreamForType >> transType;
40 0 : HCCL_INFO("[CollCommAicpu][ParsePackData] transType[%u]", transType);
41 0 : if (transType == Hccl::TransportType::UB) {
42 0 : std::unique_ptr<Hccl::UbTransportLiteImpl> ubTransportLiteImpl;
43 0 : EXCEPTION_CATCH((ubTransportLiteImpl = std::make_unique<Hccl::UbTransportLiteImpl>(transpUniqueId)),
44 : return HCCL_E_PTR);
45 0 : CHK_SMART_PTR_NULL(ubTransportLiteImpl);
46 :
47 0 : handle = reinterpret_cast<uint64_t>(ubTransportLiteImpl.get());
48 0 : ubTransportMap_.insert({handle, std::move(ubTransportLiteImpl)});
49 0 : } else {
50 0 : HCCL_ERROR("[AicpuChannelProcess][%s] transType[%u] is invalid", __func__, transType);
51 0 : return HCCL_E_PARA;
52 : }
53 :
54 0 : return HCCL_SUCCESS;
55 0 : }
56 :
57 0 : HcclResult AicpuChannelProcess::InitUrmaChannel(HcclChannelUrmaRes *commParam)
58 : {
59 0 : HCCL_INFO("[HcclCommAicpu][%s] commParam->uniqueIdAddr[%p], commParam->uniqueIdSize[%u]",
60 : __func__, commParam->uniqueIdAddr, commParam->uniqueIdSize);
61 :
62 0 : u8* currentSrcAddr = reinterpret_cast<u8*>(commParam->uniqueIdAddr);
63 0 : u32* addSize = reinterpret_cast<u32*>(commParam->channelSizeAddr);
64 0 : for (u32 index = 0; index < commParam->listNum; index++) {
65 0 : std::vector<char> data(*addSize);
66 :
67 0 : CHK_SAFETY_FUNC_RET(memcpy_s(data.data(), data.size(), currentSrcAddr, *addSize));
68 0 : currentSrcAddr += *addSize;
69 0 : addSize++;
70 : Hccl::AicpuResPackageHelper helper;
71 0 : auto dataVec = helper.ParsePackedData(data);
72 :
73 0 : Hccl::AicpuResMgrType resType = Hccl::AicpuResMgrType::STREAM;
74 0 : if (static_cast<u32>(resType) >= dataVec.size()) {
75 0 : HCCL_ERROR("[HcclCommAicpu][%s] fail, resType[%d], dataVec size[%u]", __func__, resType, dataVec.size());
76 0 : return HCCL_E_PARA;
77 : }
78 : ChannelHandle channelHandle;
79 0 : CHK_RET(ParsePackData(dataVec[resType].data, channelHandle));
80 :
81 0 : if (commParam->ctxList != nullptr) {
82 : // ctx模式:device侧填充abiHeader + deviceChannel
83 0 : auto **ctxList = reinterpret_cast<HcommAicpuChannelCtx**>(commParam->ctxList);
84 0 : ctxList[index]->abiHeader.version = HCOMM_AICPU_CHANNEL_CTX_VERSION;
85 0 : ctxList[index]->abiHeader.magicWord = HCOMM_AICPU_CHANNEL_CTX_MAGIC_WORD;
86 0 : ctxList[index]->abiHeader.size = sizeof(HcommAicpuChannelCtx);
87 0 : ctxList[index]->deviceChannel = reinterpret_cast<void*>(channelHandle);
88 : } else {
89 0 : ChannelHandle* channelList = reinterpret_cast<ChannelHandle*>(commParam->channelList);
90 0 : channelList[index] = channelHandle;
91 : }
92 0 : HCCL_INFO("[HcclCommAicpu][%s] index[%u], currentSrcAddr[%p], channelSizeAddr[%p], channelHandle[0x%llx]",
93 : __func__, index, currentSrcAddr, commParam->channelSizeAddr, channelHandle);
94 0 : }
95 :
96 0 : return HCCL_SUCCESS;
97 : }
98 :
99 0 : HcclResult AicpuChannelProcess::AicpuChannelInit(HcclChannelUrmaRes *commParam)
100 : {
101 0 : HCCL_INFO("[AicpuChannelProcess][%s] commParam->channelList[%p], commParam->listNum[%u], commParam->uniqueIdAddr[%p], "
102 : "commParam->uniqueIdSize[%u]", __func__, commParam->channelList, commParam->listNum, commParam->uniqueIdAddr,
103 : commParam->uniqueIdSize);
104 :
105 0 : CHK_RET(hrtSetWorkModeAicpu(true));
106 0 : CHK_RET(hrtSetlocalDevice(commParam->deviceLogicId));
107 0 : CHK_RET(hrtSetlocalDeviceType(static_cast<DevType>(commParam->deviceType)));
108 :
109 0 : std::lock_guard<std::mutex> addLock(mutex_);
110 :
111 0 : HcclResult ret = InitUrmaChannel(commParam);
112 0 : CHK_PRT_RET(ret != HCCL_SUCCESS,
113 : HCCL_ERROR("[AicpuChannelProcess][AicpuChannelInit]errNo[0x%016llx] Failed to init channels",
114 : HCCL_ERROR_CODE(ret)), ret);
115 :
116 0 : HCCL_INFO("[AicpuChannelProcess][%s] aicpuTask End.", __func__);
117 0 : return HCCL_SUCCESS;
118 0 : }
119 :
120 : namespace {
121 :
122 1 : void RollbackDestroy(DevAicpuTsChannelMgr &mgr, const std::vector<ChannelHandle> &rollback)
123 : {
124 1 : for (const auto &h : rollback) {
125 0 : if (mgr.DestroyChannel(h)) {
126 0 : HCCL_DEBUG("[AicpuChannelProcess][%s] rollback destroyed handle[0x%llx]", __func__, h);
127 : } else {
128 0 : HCCL_WARNING("[AicpuChannelProcess][%s] rollback failed to destroy handle[0x%llx]", __func__, h);
129 : }
130 : }
131 1 : }
132 :
133 2 : HcclResult CreateSingleHcommChannel(DevAicpuTsChannelMgr &mgr, void *dp, u64 sz,
134 : const HcommDeviceInfo &deviceInfo, hcomm::HcommChannelKind kind,
135 : HcommChannelRes *commParam, u32 index, ChannelHandle *channelList,
136 : std::vector<ChannelHandle> &rollback)
137 : {
138 2 : DevAicpuTsChannel *channel = mgr.GetOrCreateAicpuTsChannel(kind);
139 2 : if (channel == nullptr) {
140 1 : HCCL_ERROR("[AicpuChannelProcess][%s] index[%u] unsupported kind[%u]", __func__, index,
141 : static_cast<uint32_t>(kind));
142 1 : RollbackDestroy(mgr, rollback);
143 1 : return HCCL_E_NOT_SUPPORT;
144 : }
145 1 : CHK_PTR_NULL(dp);
146 1 : ChannelHandle h{};
147 1 : HcclResult pret = channel->Create(dp, sz, deviceInfo, h);
148 1 : if (pret != HCCL_SUCCESS) {
149 0 : HCCL_ERROR("[AicpuChannelProcess][%s] parse fail at index[%u]", __func__, index);
150 0 : RollbackDestroy(mgr, rollback);
151 0 : return pret;
152 : }
153 1 : if (commParam->ctxList != nullptr) {
154 0 : auto **ctxList = reinterpret_cast<HcommAicpuChannelCtx**>(commParam->ctxList);
155 0 : ctxList[index]->abiHeader.version = HCOMM_AICPU_CHANNEL_CTX_VERSION;
156 0 : ctxList[index]->abiHeader.magicWord = HCOMM_AICPU_CHANNEL_CTX_MAGIC_WORD;
157 0 : ctxList[index]->abiHeader.size = sizeof(HcommAicpuChannelCtx);
158 0 : ctxList[index]->deviceChannel = reinterpret_cast<void*>(h);
159 : } else {
160 1 : channelList[index] = h;
161 : }
162 1 : rollback.push_back(h);
163 1 : return HCCL_SUCCESS;
164 : }
165 :
166 : } // namespace
167 :
168 4 : HcclResult AicpuChannelProcess::InitHcommChannelRes(HcommChannelRes *commParam)
169 : {
170 4 : CHK_PTR_NULL(commParam);
171 3 : HCCL_INFO("[AicpuChannelProcess][%s] channelList[%p], listNum[%u]", __func__, commParam->channelList,
172 : commParam->listNum);
173 :
174 3 : CHK_PTR_NULL(commParam->channelList);
175 2 : CHK_PTR_NULL(commParam->channelDataListAddr);
176 2 : CHK_PTR_NULL(commParam->channelDataSizeListAddr);
177 2 : CHK_PTR_NULL(commParam->channelTypeListAddr);
178 :
179 2 : CHK_RET(hrtSetWorkModeAicpu(true));
180 2 : CHK_RET(hrtSetlocalDevice(commParam->deviceInfo.deviceLogicId));
181 2 : CHK_RET(hrtSetlocalDeviceType(static_cast<DevType>(commParam->deviceInfo.deviceType)));
182 :
183 2 : void **dataList = reinterpret_cast<void **>(commParam->channelDataListAddr);
184 2 : auto *sizeList = reinterpret_cast<u64 *>(commParam->channelDataSizeListAddr);
185 2 : auto *typeList = reinterpret_cast<u32 *>(commParam->channelTypeListAddr);
186 2 : auto *channelList = reinterpret_cast<ChannelHandle *>(commParam->channelList);
187 :
188 2 : auto &mgr = DevAicpuTsChannelMgr::Instance();
189 2 : std::vector<ChannelHandle> rollback;
190 2 : rollback.reserve(commParam->listNum);
191 :
192 2 : std::lock_guard<std::mutex> addLock(mutex_);
193 3 : for (u32 index = 0; index < commParam->listNum; ++index) {
194 2 : hcomm::HcommChannelKind kind = static_cast<hcomm::HcommChannelKind>(typeList[index]);
195 2 : CHK_RET(CreateSingleHcommChannel(mgr, dataList[index], sizeList[index],
196 : commParam->deviceInfo, kind, commParam, index, channelList, rollback));
197 1 : HCCL_INFO("[AicpuChannelProcess][%s] index[%u] channelHandle[0x%llx]", __func__, index,
198 : commParam->ctxList != nullptr ? 0 : channelList[index]);
199 : }
200 :
201 1 : HCCL_INFO("[AicpuChannelProcess][%s] aicpu_task End.", __func__);
202 1 : return HCCL_SUCCESS;
203 2 : }
204 :
205 0 : HcclResult AicpuChannelProcess::AicpuChannelDestroy(HcclChannelUrmaRes *commParam)
206 : {
207 0 : HCCL_INFO("[AicpuChannelProcess][%s] commParam->channelList[%p], commParam->listNum[%u]",
208 : __func__, commParam->channelList, commParam->listNum);
209 :
210 0 : auto &mgr = DevAicpuTsChannelMgr::Instance();
211 0 : std::lock_guard<std::mutex> addLock(mutex_);
212 :
213 0 : ChannelHandle* channelList = reinterpret_cast<ChannelHandle*>(commParam->channelList);
214 0 : for (u32 index = 0; index < commParam->listNum; ++index) {
215 0 : ChannelHandle handle = channelList[index];
216 :
217 0 : auto it = ubTransportMap_.find(handle);
218 0 : if (it != ubTransportMap_.end()) {
219 0 : ubTransportMap_.erase(it);
220 0 : HCCL_DEBUG("[AicpuChannelProcess][%s] destroyed ub handle[0x%llx]", __func__, handle);
221 0 : continue;
222 : }
223 :
224 0 : if (mgr.DestroyChannel(handle)) {
225 0 : HCCL_DEBUG("[AicpuChannelProcess][%s] destroyed hcomm res handle[0x%llx]", __func__, handle);
226 0 : continue;
227 : }
228 :
229 0 : HCCL_WARNING("[AicpuChannelProcess][%s] handle[0x%llx] not found in ub/hcomm maps, maybe already destroyed?",
230 : __func__, handle);
231 : }
232 :
233 0 : HCCL_INFO("[AicpuChannelProcess][%s] aicpu_task End.", __func__);
234 0 : return HCCL_SUCCESS;
235 0 : }
|