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 "ccu_wqebb_mgr_v1.h"
12 :
13 : #include <vector>
14 :
15 : #include "ccu_res_specs.h"
16 :
17 : namespace hcomm {
18 :
19 : // 计算 num 的以 2 为底的对数后移位,相当于向上最接近的 2 的整数次幂
20 155 : static uint32_t RoundUpToNextPowerOfTwo(uint32_t num)
21 : {
22 155 : if (num == 0) {
23 0 : return 1;
24 : }
25 :
26 155 : num--;
27 155 : num |= num >> 1;
28 155 : num |= num >> Hccl::SHIFT_2BITS;
29 155 : num |= num >> Hccl::SHIFT_4BITS;
30 155 : num |= num >> Hccl::SHIFT_8BITS;
31 155 : num |= num >> Hccl::SHIFT_16BITS;
32 155 : return num + 1;
33 : }
34 :
35 155 : static uint32_t GetWqeBBReqSizeBySqSize(uint32_t sqSize)
36 : {
37 155 : if (sqSize < CCU_MIN_SQ_DEPTH) {
38 0 : HCCL_WARNING("[CcuJettyCtxMgr][%s] sqSize[%u] is too small, reset to [%u].",
39 : __func__, sqSize, CCU_MIN_SQ_DEPTH);
40 0 : return CCU_MIN_SQ_DEPTH;
41 : }
42 :
43 : // WQE basic block 的 size 必须是 2 的整数次幂,向上取整
44 155 : uint32_t wqeBBReqNum = RoundUpToNextPowerOfTwo(sqSize);
45 155 : if (wqeBBReqNum != sqSize) {
46 0 : HCCL_WARNING("[CcuJettyCtxMgr][%s] sqSize[%u] is not power of 2, reset to [%u].",
47 : __func__, sqSize, wqeBBReqNum);
48 : }
49 :
50 155 : if (sqSize > CCU_MAX_SQ_DEPTH) {
51 0 : HCCL_WARNING("[CcuJettyCtxMgr][%s] sqSize[%u] is too large, reset to [%u].",
52 : __func__, sqSize, CCU_MAX_SQ_DEPTH);
53 0 : return CCU_MAX_SQ_DEPTH;
54 : }
55 :
56 155 : return wqeBBReqNum;
57 : }
58 :
59 142 : HcclResult CcuWqeBBMgrV1::Init()
60 : {
61 142 : uint32_t wqeBBNum = 0; // 获取失败或为0场景,分配将按资源不足操作
62 142 : (void)CcuResSpecifications::GetInstance(devLogicId_).GetWqeBBNum(dieId_, wqeBBNum);
63 142 : idAllocator_.reset(new (std::nothrow) CcuResIdAllocator(wqeBBNum));
64 142 : CHK_PTR_NULL(idAllocator_);
65 142 : return HcclResult::HCCL_SUCCESS;
66 : }
67 :
68 155 : HcclResult CcuWqeBBMgrV1::Alloc(const WqeBBReq& wqeBBReq, ResInfo &wqeBBInfo)
69 : {
70 155 : uint32_t wqeBBReqSize = GetWqeBBReqSizeBySqSize(wqeBBReq.sqSize);
71 155 : std::vector<ResInfo> resInfo;
72 310 : auto ret = idAllocator_->Alloc(wqeBBReqSize, true, resInfo, "ResType::WqeBB"); // wqebb资源要求连续
73 155 : if (ret == HcclResult::HCCL_E_UNAVAIL) {
74 0 : HCCL_WARNING("[CcuWqeBBMgrV1][%s] failed, left resources are not enough, "
75 : "wqeBBReq.sqSize[%u], wqeBBSize[%u]", __func__,
76 : wqeBBReq.sqSize, wqeBBReqSize);
77 0 : return ret;
78 : }
79 155 : CHK_RET(ret);
80 :
81 155 : wqeBBInfo = resInfo[0]; // 分配连续资源包含1个元素
82 155 : return ret;
83 155 : }
84 :
85 13 : HcclResult CcuWqeBBMgrV1::Release(const ResInfo &wqeBBInfo)
86 : {
87 13 : auto ret = idAllocator_->Release(wqeBBInfo.startId, wqeBBInfo.num);
88 13 : CHK_PRT_RET(ret != HcclResult::HCCL_SUCCESS,
89 : HCCL_ERROR("[CcuWqeBBMgrV1][%s] failed, wqe basic block resource info[%s]",
90 : __func__, wqeBBInfo.Describe().c_str()),
91 : ret);
92 :
93 13 : return HcclResult::HCCL_SUCCESS;
94 : }
95 : }; // namespace hcomm
|