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 : #ifndef ENDPOINT_PAIR_H
12 : #define ENDPOINT_PAIR_H
13 :
14 : #include <memory>
15 : #include <vector>
16 : #include "channels/channel.h"
17 : #include "endpoint.h"
18 : #include "socket_mgr.h"
19 : #include "../../../../legacy/ascend950/unified_platform/resource/socket/socket.h"
20 : #include "../../../../legacy/ascend950/framework/resource_manager/socket/socket_manager.h"
21 :
22 : using EndpointDescPair = std::pair<EndpointDesc, EndpointDesc>;
23 :
24 : // 重载 == 操作符,用于 EndpointDesc 在 std::unordered_map 比较
25 147 : inline bool operator==(const EndpointDesc& a, const EndpointDesc& b) noexcept {
26 147 : return std::memcmp(&a, &b, sizeof(EndpointDesc)) == 0;
27 : }
28 :
29 : namespace std {
30 :
31 : template <>
32 : struct hash<EndpointDesc> {
33 174 : size_t operator()(const EndpointDesc& e) const noexcept {
34 : // FNV-1a(64位)对字节序列做hash
35 174 : const uint8_t* p = reinterpret_cast<const uint8_t*>(&e);
36 174 : size_t h = sizeof(size_t) == 8
37 : ? static_cast<size_t>(14695981039346656037ull)
38 : : static_cast<size_t>(2166136261u);
39 :
40 174 : const size_t prime = sizeof(size_t) == 8
41 : ? static_cast<size_t>(1099511628211ull)
42 : : static_cast<size_t>(16777619u);
43 :
44 28014 : for (size_t i = 0; i < sizeof(EndpointDesc); ++i) {
45 27840 : h ^= static_cast<size_t>(p[i]);
46 27840 : h *= prime;
47 : }
48 174 : return h;
49 : }
50 : };
51 :
52 : template <>
53 : struct hash<EndpointDescPair> {
54 78 : size_t operator()(const EndpointDescPair& p) const noexcept {
55 78 : size_t h1 = std::hash<EndpointDesc>{}(p.first);
56 78 : size_t h2 = std::hash<EndpointDesc>{}(p.second);
57 78 : size_t h = h1;
58 78 : h ^= h2 + 0x9e3779b97f4a7c15ULL + (h << 6) + (h >> 2);
59 78 : return h;
60 : }
61 : };
62 :
63 : } // namespace std
64 :
65 : namespace hcomm {
66 : /**
67 : * @note 职责:通信设备Endpoint对(EndpointPair,或连接)的C++类声明,
68 : * 管理该Endpoint对上的本地和远端注册内存、多个Channel、以及socket等。两个Endpoint的通信协议一致。
69 : */
70 : class EndpointPair {
71 : public:
72 11 : EndpointPair(EndpointDesc localEndpointDesc, EndpointDesc remoteEndpointDesc,
73 : const Hccl::RankIpPortMapPtr& rankIpPortMap)
74 11 : : localEndpointDesc_(localEndpointDesc),
75 11 : remoteEndpointDesc_(remoteEndpointDesc),
76 11 : rankIpPortMap_(rankIpPortMap)
77 : {
78 11 : }
79 : ~EndpointPair();
80 :
81 : HcclResult Init();
82 :
83 : // 临时方案:新增临时接口用于支持混跑
84 : HcclResult GetSocket(const uint32_t myRank, const uint32_t rmtRank,
85 : const std::string &socketTag, u32 reuseIdx, const uint32_t listenPort, Hccl::Socket *&socket, uint32_t devicePhyId, uint32_t remoteDevicePhyId);
86 : HcclResult GetHostSocketWithRank(const uint32_t myRank, const uint32_t rmtRank, const std::string &socketTag,
87 : const uint32_t listenPort, u32 reuseIdx, Hccl::Socket*& socket);
88 :
89 : HcclResult ServerInit(const uint32_t myRank, const uint32_t rmtRank,
90 : const std::string &socketTag, u32 reuseIdx, uint32_t devicePhyId, uint32_t remoteDevicePhyId);
91 : HcclResult GetConnectedSocket(const uint32_t myRank, const uint32_t rmtRank,
92 : const std::string &socketTag, u32 reuseIdx, const uint32_t listenPort,
93 : Hccl::Socket*& socket, uint32_t devicePhyId, uint32_t remoteDevicePhyId);
94 :
95 : HcclResult CreateChannel(EndpointHandle endpointHandle, CommEngine engine, u32 reuseIdx,
96 : HcommChannelDesc *channelDescs, ChannelHandle *channels);
97 :
98 : HcclResult DestroyChannel(CommEngine engine, u32 reuseIdx);
99 :
100 : bool IsChannelNotExist(CommEngine engine, u32 reuseIdx);
101 :
102 : const std::unordered_map<CommEngine, std::vector<ChannelHandle>>& GetChannelHandles();
103 :
104 : private:
105 : HcclResult EnsureSocketMgrCompat(const uint32_t myRank, const std::string &socketTag);
106 : Hccl::SocketConfig BuildSocketConfig(const Hccl::LinkData &linkData, const std::string &socketTag);
107 : HcclResult HandleHostSocketOrBuildLinkData(const uint32_t myRank, const uint32_t rmtRank,
108 : const std::string &socketTag, u32 reuseIdx, const uint32_t listenPort, Hccl::Socket*& socket,
109 : uint32_t devicePhyId, uint32_t remoteDevicePhyId, Hccl::LinkData &linkData, bool &isHost);
110 : HcclResult GetSocketInternal(const uint32_t myRank, const uint32_t rmtRank,
111 : const std::string &socketTag, u32 reuseIdx, const uint32_t listenPort,
112 : Hccl::Socket*& socket, uint32_t devicePhyId, uint32_t remoteDevicePhyId, bool connectMode);
113 :
114 : EndpointDesc localEndpointDesc_{};
115 : EndpointDesc remoteEndpointDesc_{};
116 : std::unique_ptr<Hccl::SocketManager> socketMgrCompat_;
117 : std::unordered_map<CommEngine, std::vector<ChannelHandle>> channelHandles_{};
118 : Hccl::RankIpPortMapPtr rankIpPortMap_;
119 : uint32_t devicePhyId_{};
120 : std::unique_ptr<SocketMgr> socketMgr_;
121 : };
122 :
123 : } // namespace hcomm
124 :
125 : #endif // ENDPOINT_PAIR_H
|