nvidia-nccl-cu12 2.20.3__py3-none-manylinux2014_aarch64.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- nvidia/__init__.py +0 -0
- nvidia/nccl/__init__.py +0 -0
- nvidia/nccl/include/__init__.py +0 -0
- nvidia/nccl/include/nccl.h +448 -0
- nvidia/nccl/include/nccl_net.h +456 -0
- nvidia/nccl/lib/__init__.py +0 -0
- nvidia/nccl/lib/libnccl.so.2 +0 -0
- nvidia_nccl_cu12-2.20.3.dist-info/License.txt +31 -0
- nvidia_nccl_cu12-2.20.3.dist-info/METADATA +35 -0
- nvidia_nccl_cu12-2.20.3.dist-info/RECORD +12 -0
- nvidia_nccl_cu12-2.20.3.dist-info/WHEEL +5 -0
- nvidia_nccl_cu12-2.20.3.dist-info/top_level.txt +1 -0
nvidia/__init__.py
ADDED
|
File without changes
|
nvidia/nccl/__init__.py
ADDED
|
File without changes
|
|
File without changes
|
|
@@ -0,0 +1,448 @@
|
|
|
1
|
+
/*************************************************************************
|
|
2
|
+
* Copyright (c) 2015-2021, NVIDIA CORPORATION. All rights reserved.
|
|
3
|
+
*
|
|
4
|
+
* See LICENSE.txt for license information
|
|
5
|
+
************************************************************************/
|
|
6
|
+
|
|
7
|
+
#ifndef NCCL_H_
|
|
8
|
+
#define NCCL_H_
|
|
9
|
+
|
|
10
|
+
#include <cuda_runtime.h>
|
|
11
|
+
#include <cuda_fp16.h>
|
|
12
|
+
#if CUDART_VERSION >= 11000
|
|
13
|
+
#include <cuda_bf16.h>
|
|
14
|
+
#endif
|
|
15
|
+
|
|
16
|
+
#define NCCL_MAJOR 2
|
|
17
|
+
#define NCCL_MINOR 20
|
|
18
|
+
#define NCCL_PATCH 3
|
|
19
|
+
#define NCCL_SUFFIX ""
|
|
20
|
+
|
|
21
|
+
#define NCCL_VERSION_CODE 22003
|
|
22
|
+
#define NCCL_VERSION(X,Y,Z) (((X) <= 2 && (Y) <= 8) ? (X) * 1000 + (Y) * 100 + (Z) : (X) * 10000 + (Y) * 100 + (Z))
|
|
23
|
+
|
|
24
|
+
#ifdef __cplusplus
|
|
25
|
+
extern "C" {
|
|
26
|
+
#endif
|
|
27
|
+
|
|
28
|
+
#include <limits.h>
|
|
29
|
+
/* Opaque handle to communicator */
|
|
30
|
+
typedef struct ncclComm* ncclComm_t;
|
|
31
|
+
#define NCCL_COMM_NULL NULL
|
|
32
|
+
|
|
33
|
+
#define NCCL_UNIQUE_ID_BYTES 128
|
|
34
|
+
typedef struct { char internal[NCCL_UNIQUE_ID_BYTES]; } ncclUniqueId;
|
|
35
|
+
|
|
36
|
+
/* Error type */
|
|
37
|
+
typedef enum { ncclSuccess = 0,
|
|
38
|
+
ncclUnhandledCudaError = 1,
|
|
39
|
+
ncclSystemError = 2,
|
|
40
|
+
ncclInternalError = 3,
|
|
41
|
+
ncclInvalidArgument = 4,
|
|
42
|
+
ncclInvalidUsage = 5,
|
|
43
|
+
ncclRemoteError = 6,
|
|
44
|
+
ncclInProgress = 7,
|
|
45
|
+
ncclNumResults = 8 } ncclResult_t;
|
|
46
|
+
|
|
47
|
+
#define NCCL_CONFIG_UNDEF_INT INT_MIN
|
|
48
|
+
#define NCCL_CONFIG_UNDEF_PTR NULL
|
|
49
|
+
#define NCCL_SPLIT_NOCOLOR -1
|
|
50
|
+
|
|
51
|
+
/* Communicator configuration. Users can assign value to attributes to specify the
|
|
52
|
+
* behavior of a communicator. */
|
|
53
|
+
typedef struct ncclConfig_v21700 {
|
|
54
|
+
/* attributes that users should never touch. */
|
|
55
|
+
size_t size;
|
|
56
|
+
unsigned int magic;
|
|
57
|
+
unsigned int version;
|
|
58
|
+
/* attributes that users are able to customize. */
|
|
59
|
+
int blocking;
|
|
60
|
+
int cgaClusterSize;
|
|
61
|
+
int minCTAs;
|
|
62
|
+
int maxCTAs;
|
|
63
|
+
const char *netName;
|
|
64
|
+
int splitShare;
|
|
65
|
+
} ncclConfig_t;
|
|
66
|
+
|
|
67
|
+
/* Config initializer must be assigned to initialize config structure when it is created.
|
|
68
|
+
* Not initialized config will result in NCCL error. */
|
|
69
|
+
#define NCCL_CONFIG_INITIALIZER { \
|
|
70
|
+
sizeof(ncclConfig_t), /* size */ \
|
|
71
|
+
0xcafebeef, /* magic */ \
|
|
72
|
+
NCCL_VERSION(NCCL_MAJOR, NCCL_MINOR, NCCL_PATCH), /* version */ \
|
|
73
|
+
NCCL_CONFIG_UNDEF_INT, /* blocking */ \
|
|
74
|
+
NCCL_CONFIG_UNDEF_INT, /* cgaClusterSize */ \
|
|
75
|
+
NCCL_CONFIG_UNDEF_INT, /* minCTAs */ \
|
|
76
|
+
NCCL_CONFIG_UNDEF_INT, /* maxCTAs */ \
|
|
77
|
+
NCCL_CONFIG_UNDEF_PTR, /* netName */ \
|
|
78
|
+
NCCL_CONFIG_UNDEF_INT /* splitShare */ \
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
/* NCCL malloc and free function for all types of NCCL optimizations
|
|
82
|
+
* (e.g. user buffer registration). The actual allocated size might
|
|
83
|
+
* be larger than requested due to granularity requirement. */
|
|
84
|
+
ncclResult_t ncclMemAlloc(void** ptr, size_t size);
|
|
85
|
+
ncclResult_t pncclMemAlloc(void** ptr, size_t size);
|
|
86
|
+
|
|
87
|
+
ncclResult_t ncclMemFree(void *ptr);
|
|
88
|
+
ncclResult_t pncclMemFree(void *ptr);
|
|
89
|
+
|
|
90
|
+
/* Return the NCCL_VERSION_CODE of the NCCL library in the supplied integer.
|
|
91
|
+
* This integer is coded with the MAJOR, MINOR and PATCH level of the
|
|
92
|
+
* NCCL library
|
|
93
|
+
*/
|
|
94
|
+
ncclResult_t ncclGetVersion(int *version);
|
|
95
|
+
ncclResult_t pncclGetVersion(int *version);
|
|
96
|
+
|
|
97
|
+
/* Generates an Id to be used in ncclCommInitRank. ncclGetUniqueId should be
|
|
98
|
+
* called once and the Id should be distributed to all ranks in the
|
|
99
|
+
* communicator before calling ncclCommInitRank. */
|
|
100
|
+
ncclResult_t ncclGetUniqueId(ncclUniqueId* uniqueId);
|
|
101
|
+
ncclResult_t pncclGetUniqueId(ncclUniqueId* uniqueId);
|
|
102
|
+
|
|
103
|
+
/* Create a new communicator (multi thread/process version) with a configuration
|
|
104
|
+
* set by users. */
|
|
105
|
+
ncclResult_t ncclCommInitRankConfig(ncclComm_t* comm, int nranks, ncclUniqueId commId, int rank, ncclConfig_t* config);
|
|
106
|
+
ncclResult_t pncclCommInitRankConfig(ncclComm_t* comm, int nranks, ncclUniqueId commId, int rank, ncclConfig_t* config);
|
|
107
|
+
|
|
108
|
+
/* Creates a new communicator (multi thread/process version).
|
|
109
|
+
* rank must be between 0 and nranks-1 and unique within a communicator clique.
|
|
110
|
+
* Each rank is associated to a CUDA device, which has to be set before calling
|
|
111
|
+
* ncclCommInitRank.
|
|
112
|
+
* ncclCommInitRank implicitly syncronizes with other ranks, so it must be
|
|
113
|
+
* called by different threads/processes or use ncclGroupStart/ncclGroupEnd. */
|
|
114
|
+
ncclResult_t ncclCommInitRank(ncclComm_t* comm, int nranks, ncclUniqueId commId, int rank);
|
|
115
|
+
ncclResult_t pncclCommInitRank(ncclComm_t* comm, int nranks, ncclUniqueId commId, int rank);
|
|
116
|
+
|
|
117
|
+
/* Creates a clique of communicators (single process version).
|
|
118
|
+
* This is a convenience function to create a single-process communicator clique.
|
|
119
|
+
* Returns an array of ndev newly initialized communicators in comm.
|
|
120
|
+
* comm should be pre-allocated with size at least ndev*sizeof(ncclComm_t).
|
|
121
|
+
* If devlist is NULL, the first ndev CUDA devices are used.
|
|
122
|
+
* Order of devlist defines user-order of processors within the communicator. */
|
|
123
|
+
ncclResult_t ncclCommInitAll(ncclComm_t* comm, int ndev, const int* devlist);
|
|
124
|
+
ncclResult_t pncclCommInitAll(ncclComm_t* comm, int ndev, const int* devlist);
|
|
125
|
+
|
|
126
|
+
/* Finalize a communicator. ncclCommFinalize flushes all issued communications,
|
|
127
|
+
* and marks communicator state as ncclInProgress. The state will change to ncclSuccess
|
|
128
|
+
* when the communicator is globally quiescent and related resources are freed; then,
|
|
129
|
+
* calling ncclCommDestroy can locally free the rest of the resources (e.g. communicator
|
|
130
|
+
* itself) without blocking. */
|
|
131
|
+
ncclResult_t ncclCommFinalize(ncclComm_t comm);
|
|
132
|
+
ncclResult_t pncclCommFinalize(ncclComm_t comm);
|
|
133
|
+
|
|
134
|
+
/* Frees local resources associated with communicator object. */
|
|
135
|
+
ncclResult_t ncclCommDestroy(ncclComm_t comm);
|
|
136
|
+
ncclResult_t pncclCommDestroy(ncclComm_t comm);
|
|
137
|
+
|
|
138
|
+
/* Frees resources associated with communicator object and aborts any operations
|
|
139
|
+
* that might still be running on the device. */
|
|
140
|
+
ncclResult_t ncclCommAbort(ncclComm_t comm);
|
|
141
|
+
ncclResult_t pncclCommAbort(ncclComm_t comm);
|
|
142
|
+
|
|
143
|
+
/* Creates one or more communicators from an existing one.
|
|
144
|
+
* Ranks with the same color will end up in the same communicator.
|
|
145
|
+
* Within the new communicator, key will be used to order ranks.
|
|
146
|
+
* NCCL_SPLIT_NOCOLOR as color will indicate the rank will not be part of any group
|
|
147
|
+
* and will therefore return a NULL communicator.
|
|
148
|
+
* If config is NULL, the new communicator will inherit the original communicator's
|
|
149
|
+
* configuration*/
|
|
150
|
+
ncclResult_t ncclCommSplit(ncclComm_t comm, int color, int key, ncclComm_t *newcomm, ncclConfig_t* config);
|
|
151
|
+
ncclResult_t pncclCommSplit(ncclComm_t comm, int color, int key, ncclComm_t *newcomm, ncclConfig_t* config);
|
|
152
|
+
|
|
153
|
+
/* Returns a string for each error code. */
|
|
154
|
+
const char* ncclGetErrorString(ncclResult_t result);
|
|
155
|
+
const char* pncclGetErrorString(ncclResult_t result);
|
|
156
|
+
|
|
157
|
+
/* Returns a human-readable message of the last error that occurred. */
|
|
158
|
+
const char* ncclGetLastError(ncclComm_t comm);
|
|
159
|
+
const char* pncclGetLastError(ncclComm_t comm);
|
|
160
|
+
|
|
161
|
+
/* Checks whether the comm has encountered any asynchronous errors */
|
|
162
|
+
ncclResult_t ncclCommGetAsyncError(ncclComm_t comm, ncclResult_t *asyncError);
|
|
163
|
+
ncclResult_t pncclCommGetAsyncError(ncclComm_t comm, ncclResult_t *asyncError);
|
|
164
|
+
|
|
165
|
+
/* Gets the number of ranks in the communicator clique. */
|
|
166
|
+
ncclResult_t ncclCommCount(const ncclComm_t comm, int* count);
|
|
167
|
+
ncclResult_t pncclCommCount(const ncclComm_t comm, int* count);
|
|
168
|
+
|
|
169
|
+
/* Returns the cuda device number associated with the communicator. */
|
|
170
|
+
ncclResult_t ncclCommCuDevice(const ncclComm_t comm, int* device);
|
|
171
|
+
ncclResult_t pncclCommCuDevice(const ncclComm_t comm, int* device);
|
|
172
|
+
|
|
173
|
+
/* Returns the user-ordered "rank" associated with the communicator. */
|
|
174
|
+
ncclResult_t ncclCommUserRank(const ncclComm_t comm, int* rank);
|
|
175
|
+
ncclResult_t pncclCommUserRank(const ncclComm_t comm, int* rank);
|
|
176
|
+
|
|
177
|
+
|
|
178
|
+
/* Register CUDA buffer for zero-copy operation */
|
|
179
|
+
ncclResult_t ncclCommRegister(const ncclComm_t comm, void* buff, size_t size, void** handle);
|
|
180
|
+
ncclResult_t pncclCommRegister(const ncclComm_t comm, void* buff, size_t size, void** handle);
|
|
181
|
+
|
|
182
|
+
/* Deregister CUDA buffer */
|
|
183
|
+
ncclResult_t ncclCommDeregister(const ncclComm_t comm, void* handle);
|
|
184
|
+
ncclResult_t pncclCommDeregister(const ncclComm_t comm, void* handle);
|
|
185
|
+
|
|
186
|
+
/* Reduction operation selector */
|
|
187
|
+
typedef enum { ncclNumOps_dummy = 5 } ncclRedOp_dummy_t;
|
|
188
|
+
typedef enum { ncclSum = 0,
|
|
189
|
+
ncclProd = 1,
|
|
190
|
+
ncclMax = 2,
|
|
191
|
+
ncclMin = 3,
|
|
192
|
+
ncclAvg = 4,
|
|
193
|
+
/* ncclNumOps: The number of built-in ncclRedOp_t values. Also
|
|
194
|
+
* serves as the least possible value for dynamic ncclRedOp_t's
|
|
195
|
+
* as constructed by ncclRedOpCreate*** functions. */
|
|
196
|
+
ncclNumOps = 5,
|
|
197
|
+
/* ncclMaxRedOp: The largest valid value for ncclRedOp_t.
|
|
198
|
+
* It is defined to be the largest signed value (since compilers
|
|
199
|
+
* are permitted to use signed enums) that won't grow
|
|
200
|
+
* sizeof(ncclRedOp_t) when compared to previous NCCL versions to
|
|
201
|
+
* maintain ABI compatibility. */
|
|
202
|
+
ncclMaxRedOp = 0x7fffffff>>(32-8*sizeof(ncclRedOp_dummy_t))
|
|
203
|
+
} ncclRedOp_t;
|
|
204
|
+
|
|
205
|
+
/* Data types */
|
|
206
|
+
typedef enum { ncclInt8 = 0, ncclChar = 0,
|
|
207
|
+
ncclUint8 = 1,
|
|
208
|
+
ncclInt32 = 2, ncclInt = 2,
|
|
209
|
+
ncclUint32 = 3,
|
|
210
|
+
ncclInt64 = 4,
|
|
211
|
+
ncclUint64 = 5,
|
|
212
|
+
ncclFloat16 = 6, ncclHalf = 6,
|
|
213
|
+
ncclFloat32 = 7, ncclFloat = 7,
|
|
214
|
+
ncclFloat64 = 8, ncclDouble = 8,
|
|
215
|
+
#if defined(__CUDA_BF16_TYPES_EXIST__)
|
|
216
|
+
ncclBfloat16 = 9,
|
|
217
|
+
ncclNumTypes = 10
|
|
218
|
+
#else
|
|
219
|
+
ncclNumTypes = 9
|
|
220
|
+
#endif
|
|
221
|
+
} ncclDataType_t;
|
|
222
|
+
|
|
223
|
+
/* ncclScalarResidence_t: Location and dereferencing logic for scalar arguments. */
|
|
224
|
+
typedef enum {
|
|
225
|
+
/* ncclScalarDevice: The scalar is in device-visible memory and will be
|
|
226
|
+
* dereferenced while the collective is running. */
|
|
227
|
+
ncclScalarDevice = 0,
|
|
228
|
+
|
|
229
|
+
/* ncclScalarHostImmediate: The scalar is in host-visible memory and will be
|
|
230
|
+
* dereferenced before the ncclRedOpCreate***() function returns. */
|
|
231
|
+
ncclScalarHostImmediate = 1
|
|
232
|
+
} ncclScalarResidence_t;
|
|
233
|
+
|
|
234
|
+
/*
|
|
235
|
+
* ncclRedOpCreatePreMulSum
|
|
236
|
+
*
|
|
237
|
+
* Creates a new reduction operator which pre-multiplies input values by a given
|
|
238
|
+
* scalar locally before reducing them with peer values via summation. For use
|
|
239
|
+
* only with collectives launched against *comm* and *datatype*. The
|
|
240
|
+
* *residence* argument indicates how/when the memory pointed to by *scalar*
|
|
241
|
+
* will be dereferenced. Upon return, the newly created operator's handle
|
|
242
|
+
* is stored in *op*.
|
|
243
|
+
*/
|
|
244
|
+
ncclResult_t ncclRedOpCreatePreMulSum(ncclRedOp_t *op, void *scalar, ncclDataType_t datatype, ncclScalarResidence_t residence, ncclComm_t comm);
|
|
245
|
+
ncclResult_t pncclRedOpCreatePreMulSum(ncclRedOp_t *op, void *scalar, ncclDataType_t datatype, ncclScalarResidence_t residence, ncclComm_t comm);
|
|
246
|
+
|
|
247
|
+
/*
|
|
248
|
+
* ncclRedOpDestroy
|
|
249
|
+
*
|
|
250
|
+
* Destroys the reduction operator *op*. The operator must have been created by
|
|
251
|
+
* ncclRedOpCreatePreMul with the matching communicator *comm*. An operator may be
|
|
252
|
+
* destroyed as soon as the last NCCL function which is given that operator returns.
|
|
253
|
+
*/
|
|
254
|
+
ncclResult_t ncclRedOpDestroy(ncclRedOp_t op, ncclComm_t comm);
|
|
255
|
+
ncclResult_t pncclRedOpDestroy(ncclRedOp_t op, ncclComm_t comm);
|
|
256
|
+
|
|
257
|
+
/*
|
|
258
|
+
* Collective communication operations
|
|
259
|
+
*
|
|
260
|
+
* Collective communication operations must be called separately for each
|
|
261
|
+
* communicator in a communicator clique.
|
|
262
|
+
*
|
|
263
|
+
* They return when operations have been enqueued on the CUDA stream.
|
|
264
|
+
*
|
|
265
|
+
* Since they may perform inter-CPU synchronization, each call has to be done
|
|
266
|
+
* from a different thread or process, or need to use Group Semantics (see
|
|
267
|
+
* below).
|
|
268
|
+
*/
|
|
269
|
+
|
|
270
|
+
/*
|
|
271
|
+
* Reduce
|
|
272
|
+
*
|
|
273
|
+
* Reduces data arrays of length count in sendbuff into recvbuff using op
|
|
274
|
+
* operation.
|
|
275
|
+
* recvbuff may be NULL on all calls except for root device.
|
|
276
|
+
* root is the rank (not the CUDA device) where data will reside after the
|
|
277
|
+
* operation is complete.
|
|
278
|
+
*
|
|
279
|
+
* In-place operation will happen if sendbuff == recvbuff.
|
|
280
|
+
*/
|
|
281
|
+
ncclResult_t ncclReduce(const void* sendbuff, void* recvbuff, size_t count, ncclDataType_t datatype,
|
|
282
|
+
ncclRedOp_t op, int root, ncclComm_t comm, cudaStream_t stream);
|
|
283
|
+
ncclResult_t pncclReduce(const void* sendbuff, void* recvbuff, size_t count, ncclDataType_t datatype,
|
|
284
|
+
ncclRedOp_t op, int root, ncclComm_t comm, cudaStream_t stream);
|
|
285
|
+
|
|
286
|
+
/*
|
|
287
|
+
* (deprecated) Broadcast (in-place)
|
|
288
|
+
*
|
|
289
|
+
* Copies count values from root to all other devices.
|
|
290
|
+
* root is the rank (not the CUDA device) where data resides before the
|
|
291
|
+
* operation is started.
|
|
292
|
+
*
|
|
293
|
+
* This operation is implicitely in place.
|
|
294
|
+
*/
|
|
295
|
+
ncclResult_t ncclBcast(void* buff, size_t count, ncclDataType_t datatype, int root,
|
|
296
|
+
ncclComm_t comm, cudaStream_t stream);
|
|
297
|
+
ncclResult_t pncclBcast(void* buff, size_t count, ncclDataType_t datatype, int root,
|
|
298
|
+
ncclComm_t comm, cudaStream_t stream);
|
|
299
|
+
|
|
300
|
+
/*
|
|
301
|
+
* Broadcast
|
|
302
|
+
*
|
|
303
|
+
* Copies count values from root to all other devices.
|
|
304
|
+
* root is the rank (not the CUDA device) where data resides before the
|
|
305
|
+
* operation is started.
|
|
306
|
+
*
|
|
307
|
+
* In-place operation will happen if sendbuff == recvbuff.
|
|
308
|
+
*/
|
|
309
|
+
ncclResult_t ncclBroadcast(const void* sendbuff, void* recvbuff, size_t count, ncclDataType_t datatype, int root,
|
|
310
|
+
ncclComm_t comm, cudaStream_t stream);
|
|
311
|
+
ncclResult_t pncclBroadcast(const void* sendbuff, void* recvbuff, size_t count, ncclDataType_t datatype, int root,
|
|
312
|
+
ncclComm_t comm, cudaStream_t stream);
|
|
313
|
+
|
|
314
|
+
/*
|
|
315
|
+
* All-Reduce
|
|
316
|
+
*
|
|
317
|
+
* Reduces data arrays of length count in sendbuff using op operation, and
|
|
318
|
+
* leaves identical copies of result on each recvbuff.
|
|
319
|
+
*
|
|
320
|
+
* In-place operation will happen if sendbuff == recvbuff.
|
|
321
|
+
*/
|
|
322
|
+
ncclResult_t ncclAllReduce(const void* sendbuff, void* recvbuff, size_t count,
|
|
323
|
+
ncclDataType_t datatype, ncclRedOp_t op, ncclComm_t comm, cudaStream_t stream);
|
|
324
|
+
ncclResult_t pncclAllReduce(const void* sendbuff, void* recvbuff, size_t count,
|
|
325
|
+
ncclDataType_t datatype, ncclRedOp_t op, ncclComm_t comm, cudaStream_t stream);
|
|
326
|
+
|
|
327
|
+
/*
|
|
328
|
+
* Reduce-Scatter
|
|
329
|
+
*
|
|
330
|
+
* Reduces data in sendbuff using op operation and leaves reduced result
|
|
331
|
+
* scattered over the devices so that recvbuff on rank i will contain the i-th
|
|
332
|
+
* block of the result.
|
|
333
|
+
* Assumes sendcount is equal to nranks*recvcount, which means that sendbuff
|
|
334
|
+
* should have a size of at least nranks*recvcount elements.
|
|
335
|
+
*
|
|
336
|
+
* In-place operations will happen if recvbuff == sendbuff + rank * recvcount.
|
|
337
|
+
*/
|
|
338
|
+
ncclResult_t ncclReduceScatter(const void* sendbuff, void* recvbuff,
|
|
339
|
+
size_t recvcount, ncclDataType_t datatype, ncclRedOp_t op, ncclComm_t comm,
|
|
340
|
+
cudaStream_t stream);
|
|
341
|
+
ncclResult_t pncclReduceScatter(const void* sendbuff, void* recvbuff,
|
|
342
|
+
size_t recvcount, ncclDataType_t datatype, ncclRedOp_t op, ncclComm_t comm,
|
|
343
|
+
cudaStream_t stream);
|
|
344
|
+
|
|
345
|
+
/*
|
|
346
|
+
* All-Gather
|
|
347
|
+
*
|
|
348
|
+
* Each device gathers sendcount values from other GPUs into recvbuff,
|
|
349
|
+
* receiving data from rank i at offset i*sendcount.
|
|
350
|
+
* Assumes recvcount is equal to nranks*sendcount, which means that recvbuff
|
|
351
|
+
* should have a size of at least nranks*sendcount elements.
|
|
352
|
+
*
|
|
353
|
+
* In-place operations will happen if sendbuff == recvbuff + rank * sendcount.
|
|
354
|
+
*/
|
|
355
|
+
ncclResult_t ncclAllGather(const void* sendbuff, void* recvbuff, size_t sendcount,
|
|
356
|
+
ncclDataType_t datatype, ncclComm_t comm, cudaStream_t stream);
|
|
357
|
+
ncclResult_t pncclAllGather(const void* sendbuff, void* recvbuff, size_t sendcount,
|
|
358
|
+
ncclDataType_t datatype, ncclComm_t comm, cudaStream_t stream);
|
|
359
|
+
|
|
360
|
+
/*
|
|
361
|
+
* Send
|
|
362
|
+
*
|
|
363
|
+
* Send data from sendbuff to rank peer.
|
|
364
|
+
*
|
|
365
|
+
* Rank peer needs to call ncclRecv with the same datatype and the same count from this
|
|
366
|
+
* rank.
|
|
367
|
+
*
|
|
368
|
+
* This operation is blocking for the GPU. If multiple ncclSend and ncclRecv operations
|
|
369
|
+
* need to progress concurrently to complete, they must be fused within a ncclGroupStart/
|
|
370
|
+
* ncclGroupEnd section.
|
|
371
|
+
*/
|
|
372
|
+
ncclResult_t ncclSend(const void* sendbuff, size_t count, ncclDataType_t datatype, int peer,
|
|
373
|
+
ncclComm_t comm, cudaStream_t stream);
|
|
374
|
+
ncclResult_t pncclSend(const void* sendbuff, size_t count, ncclDataType_t datatype, int peer,
|
|
375
|
+
ncclComm_t comm, cudaStream_t stream);
|
|
376
|
+
|
|
377
|
+
/*
|
|
378
|
+
* Receive
|
|
379
|
+
*
|
|
380
|
+
* Receive data from rank peer into recvbuff.
|
|
381
|
+
*
|
|
382
|
+
* Rank peer needs to call ncclSend with the same datatype and the same count to this
|
|
383
|
+
* rank.
|
|
384
|
+
*
|
|
385
|
+
* This operation is blocking for the GPU. If multiple ncclSend and ncclRecv operations
|
|
386
|
+
* need to progress concurrently to complete, they must be fused within a ncclGroupStart/
|
|
387
|
+
* ncclGroupEnd section.
|
|
388
|
+
*/
|
|
389
|
+
ncclResult_t pncclRecv(void* recvbuff, size_t count, ncclDataType_t datatype, int peer,
|
|
390
|
+
ncclComm_t comm, cudaStream_t stream);
|
|
391
|
+
ncclResult_t ncclRecv(void* recvbuff, size_t count, ncclDataType_t datatype, int peer,
|
|
392
|
+
ncclComm_t comm, cudaStream_t stream);
|
|
393
|
+
|
|
394
|
+
/*
|
|
395
|
+
* Group semantics
|
|
396
|
+
*
|
|
397
|
+
* When managing multiple GPUs from a single thread, and since NCCL collective
|
|
398
|
+
* calls may perform inter-CPU synchronization, we need to "group" calls for
|
|
399
|
+
* different ranks/devices into a single call.
|
|
400
|
+
*
|
|
401
|
+
* Grouping NCCL calls as being part of the same collective operation is done
|
|
402
|
+
* using ncclGroupStart and ncclGroupEnd. ncclGroupStart will enqueue all
|
|
403
|
+
* collective calls until the ncclGroupEnd call, which will wait for all calls
|
|
404
|
+
* to be complete. Note that for collective communication, ncclGroupEnd only
|
|
405
|
+
* guarantees that the operations are enqueued on the streams, not that
|
|
406
|
+
* the operation is effectively done.
|
|
407
|
+
*
|
|
408
|
+
* Both collective communication and ncclCommInitRank can be used in conjunction
|
|
409
|
+
* of ncclGroupStart/ncclGroupEnd, but not together.
|
|
410
|
+
*
|
|
411
|
+
* Group semantics also allow to fuse multiple operations on the same device
|
|
412
|
+
* to improve performance (for aggregated collective calls), or to permit
|
|
413
|
+
* concurrent progress of multiple send/receive operations.
|
|
414
|
+
*/
|
|
415
|
+
|
|
416
|
+
/*
|
|
417
|
+
* Group Start
|
|
418
|
+
*
|
|
419
|
+
* Start a group call. All calls to NCCL until ncclGroupEnd will be fused into
|
|
420
|
+
* a single NCCL operation. Nothing will be started on the CUDA stream until
|
|
421
|
+
* ncclGroupEnd.
|
|
422
|
+
*/
|
|
423
|
+
ncclResult_t ncclGroupStart();
|
|
424
|
+
ncclResult_t pncclGroupStart();
|
|
425
|
+
|
|
426
|
+
/*
|
|
427
|
+
* Group End
|
|
428
|
+
*
|
|
429
|
+
* End a group call. Start a fused NCCL operation consisting of all calls since
|
|
430
|
+
* ncclGroupStart. Operations on the CUDA stream depending on the NCCL operations
|
|
431
|
+
* need to be called after ncclGroupEnd.
|
|
432
|
+
*/
|
|
433
|
+
ncclResult_t ncclGroupEnd();
|
|
434
|
+
ncclResult_t pncclGroupEnd();
|
|
435
|
+
|
|
436
|
+
/* Register CUDA buffer for zero-copy operation */
|
|
437
|
+
ncclResult_t ncclCommRegister(const ncclComm_t comm, void* buff, size_t size, void** handle);
|
|
438
|
+
ncclResult_t pncclCommRegister(const ncclComm_t comm, void* buff, size_t size, void** handle);
|
|
439
|
+
|
|
440
|
+
/* Deregister CUDA buffer */
|
|
441
|
+
ncclResult_t ncclCommDeregister(const ncclComm_t comm, void* handle);
|
|
442
|
+
ncclResult_t pncclCommDeregister(const ncclComm_t comm, void* handle);
|
|
443
|
+
|
|
444
|
+
#ifdef __cplusplus
|
|
445
|
+
} // end extern "C"
|
|
446
|
+
#endif
|
|
447
|
+
|
|
448
|
+
#endif // end include guard
|
|
@@ -0,0 +1,456 @@
|
|
|
1
|
+
/*************************************************************************
|
|
2
|
+
* Copyright (c) 2017-2022, NVIDIA CORPORATION. All rights reserved.
|
|
3
|
+
*
|
|
4
|
+
* See LICENSE.txt for license information
|
|
5
|
+
************************************************************************/
|
|
6
|
+
|
|
7
|
+
#ifndef NCCL_NET_H_
|
|
8
|
+
#define NCCL_NET_H_
|
|
9
|
+
|
|
10
|
+
#include "nccl.h"
|
|
11
|
+
#include "nccl_common.h"
|
|
12
|
+
#include "net_device.h"
|
|
13
|
+
#include <stdint.h>
|
|
14
|
+
|
|
15
|
+
#define NCCL_NET_HANDLE_MAXSIZE 128
|
|
16
|
+
|
|
17
|
+
#define NCCL_PTR_HOST 0x1
|
|
18
|
+
#define NCCL_PTR_CUDA 0x2
|
|
19
|
+
#define NCCL_PTR_DMABUF 0x4
|
|
20
|
+
|
|
21
|
+
// Maximum number of requests per comm object
|
|
22
|
+
#define NCCL_NET_MAX_REQUESTS 32
|
|
23
|
+
|
|
24
|
+
typedef struct {
|
|
25
|
+
char* name; // Used mostly for logging.
|
|
26
|
+
char* pciPath; // Path to the PCI device in /sys.
|
|
27
|
+
uint64_t guid; // Unique identifier for the NIC chip. Important for
|
|
28
|
+
// cards with multiple PCI functions (Physical or virtual).
|
|
29
|
+
int ptrSupport; // [NCCL_PTR_HOST|NCCL_PTR_CUDA|NCCL_PTR_DMABUF]
|
|
30
|
+
int regIsGlobal; // regMr is not tied to a particular comm
|
|
31
|
+
int speed; // Port speed in Mbps.
|
|
32
|
+
int port; // Port number.
|
|
33
|
+
float latency; // Network latency
|
|
34
|
+
int maxComms; // Maximum number of comms we can create
|
|
35
|
+
int maxRecvs; // Maximum number of grouped receives.
|
|
36
|
+
ncclNetDeviceType netDeviceType; // Network offload type
|
|
37
|
+
int netDeviceVersion; // Version number for network offload
|
|
38
|
+
} ncclNetProperties_v8_t;
|
|
39
|
+
|
|
40
|
+
typedef ncclNetProperties_v8_t ncclNetProperties_t;
|
|
41
|
+
|
|
42
|
+
typedef struct {
|
|
43
|
+
// Name of the network (mainly for logs)
|
|
44
|
+
const char* name;
|
|
45
|
+
// Initialize the network.
|
|
46
|
+
ncclResult_t (*init)(ncclDebugLogger_t logFunction);
|
|
47
|
+
// Return the number of adapters.
|
|
48
|
+
ncclResult_t (*devices)(int* ndev);
|
|
49
|
+
// Get various device properties.
|
|
50
|
+
ncclResult_t (*getProperties)(int dev, ncclNetProperties_v8_t* props);
|
|
51
|
+
// Create a receiving object and provide a handle to connect to it. The
|
|
52
|
+
// handle can be up to NCCL_NET_HANDLE_MAXSIZE bytes and will be exchanged
|
|
53
|
+
// between ranks to create a connection.
|
|
54
|
+
ncclResult_t (*listen)(int dev, void* handle, void** listenComm);
|
|
55
|
+
// Connect to a handle and return a sending comm object for that peer.
|
|
56
|
+
// This call must not block for the connection to be established, and instead
|
|
57
|
+
// should return successfully with sendComm == NULL with the expectation that
|
|
58
|
+
// it will be called again until sendComm != NULL.
|
|
59
|
+
// If *sendDevComm points to a valid object, then NCCL is requesting device offload for this connection
|
|
60
|
+
ncclResult_t (*connect)(int dev, void* handle, void** sendComm, ncclNetDeviceHandle_v8_t** sendDevComm);
|
|
61
|
+
// Finalize connection establishment after remote peer has called connect.
|
|
62
|
+
// This call must not block for the connection to be established, and instead
|
|
63
|
+
// should return successfully with recvComm == NULL with the expectation that
|
|
64
|
+
// it will be called again until recvComm != NULL.
|
|
65
|
+
// If *recvDevComm points to a valid object, then NCCL is requesting device offload for this connection
|
|
66
|
+
ncclResult_t (*accept)(void* listenComm, void** recvComm, ncclNetDeviceHandle_v8_t** recvDevComm);
|
|
67
|
+
// Register/Deregister memory. Comm can be either a sendComm or a recvComm.
|
|
68
|
+
// Type is either NCCL_PTR_HOST or NCCL_PTR_CUDA.
|
|
69
|
+
ncclResult_t (*regMr)(void* comm, void* data, size_t size, int type, void** mhandle);
|
|
70
|
+
/* DMA-BUF support */
|
|
71
|
+
ncclResult_t (*regMrDmaBuf)(void* comm, void* data, size_t size, int type, uint64_t offset, int fd, void** mhandle);
|
|
72
|
+
ncclResult_t (*deregMr)(void* comm, void* mhandle);
|
|
73
|
+
// Asynchronous send to a peer.
|
|
74
|
+
// May return request == NULL if the call cannot be performed (or would block)
|
|
75
|
+
ncclResult_t (*isend)(void* sendComm, void* data, int size, int tag, void* mhandle, void** request);
|
|
76
|
+
// Asynchronous recv from a peer.
|
|
77
|
+
// May return request == NULL if the call cannot be performed (or would block)
|
|
78
|
+
ncclResult_t (*irecv)(void* recvComm, int n, void** data, int* sizes, int* tags, void** mhandles, void** request);
|
|
79
|
+
// Perform a flush/fence to make sure all data received with NCCL_PTR_CUDA is
|
|
80
|
+
// visible to the GPU
|
|
81
|
+
ncclResult_t (*iflush)(void* recvComm, int n, void** data, int* sizes, void** mhandles, void** request);
|
|
82
|
+
// Test whether a request is complete. If size is not NULL, it returns the
|
|
83
|
+
// number of bytes sent/received.
|
|
84
|
+
ncclResult_t (*test)(void* request, int* done, int* sizes);
|
|
85
|
+
// Close and free send/recv comm objects
|
|
86
|
+
ncclResult_t (*closeSend)(void* sendComm);
|
|
87
|
+
ncclResult_t (*closeRecv)(void* recvComm);
|
|
88
|
+
ncclResult_t (*closeListen)(void* listenComm);
|
|
89
|
+
|
|
90
|
+
// Copy the given mhandle to a dptr in a format usable by this plugin's device code
|
|
91
|
+
ncclResult_t (*getDeviceMr)(void* comm, void* mhandle, void** dptr_mhandle);
|
|
92
|
+
|
|
93
|
+
// Notify the plugin that a recv has completed by the device
|
|
94
|
+
ncclResult_t (*irecvConsumed)(void* recvComm, int n, void* request);
|
|
95
|
+
} ncclNet_v8_t;
|
|
96
|
+
|
|
97
|
+
typedef ncclNet_v8_t ncclNet_t;
|
|
98
|
+
|
|
99
|
+
#define NCCL_NET_PLUGIN_SYMBOL ncclNetPlugin_v8
|
|
100
|
+
|
|
101
|
+
typedef struct {
|
|
102
|
+
void* mhandle;
|
|
103
|
+
void* address;
|
|
104
|
+
uint32_t size;
|
|
105
|
+
} ncclNetSGE_v8_t;
|
|
106
|
+
|
|
107
|
+
typedef struct {
|
|
108
|
+
// Name of the collective network (mainly for logs)
|
|
109
|
+
const char* name;
|
|
110
|
+
// Initialize the collective network.
|
|
111
|
+
ncclResult_t (*init)(ncclDebugLogger_t logFunction);
|
|
112
|
+
// Return the number of adapters capable of doing collective operations.
|
|
113
|
+
// If ndev returns 0, all other functions might be set to NULL.
|
|
114
|
+
ncclResult_t (*devices)(int* ndev);
|
|
115
|
+
// Get various device properties.
|
|
116
|
+
ncclResult_t (*getProperties)(int dev, ncclNetProperties_v8_t* props);
|
|
117
|
+
// Create a receiving object and provide a handle to connect to it. The
|
|
118
|
+
// handle can be up to NCCL_NET_HANDLE_MAXSIZE bytes and will be exchanged
|
|
119
|
+
// between ranks to create connections.
|
|
120
|
+
ncclResult_t (*listen)(int dev, void* handle, void** listenComm);
|
|
121
|
+
// Create a group for collective operations. handles have been created
|
|
122
|
+
// using listen() above. rank indicates caller's rank in the collective network.
|
|
123
|
+
ncclResult_t (*connect)(void* handles[], int nranks, int rank, void* listenComm, void** collComm);
|
|
124
|
+
// Returns whether a reduction operation on a data type is supported.
|
|
125
|
+
// 1 for supported, 0 otherwise.
|
|
126
|
+
ncclResult_t (*reduceSupport)(ncclDataType_t dataType, ncclRedOp_t redOp, int* supported);
|
|
127
|
+
// Register/Deregister memory. Type is either NCCL_PTR_HOST or NCCL_PTR_CUDA.
|
|
128
|
+
ncclResult_t (*regMr)(void* collComm, void* data, size_t size, int type, void** mhandle);
|
|
129
|
+
/* DMA-BUF support */
|
|
130
|
+
ncclResult_t (*regMrDmaBuf)(void* collComm, void* data, size_t size, int type, uint64_t offset, int fd, void** mhandle);
|
|
131
|
+
ncclResult_t (*deregMr)(void* collComm, void* mhandle);
|
|
132
|
+
// Performs an asynchronous allreduce operation on the collective group.
|
|
133
|
+
// May return request == NULL if the call cannot be performed (or would block).
|
|
134
|
+
ncclResult_t (*iallreduce)(void* collComm, void* sendData, void* recvData, int count,
|
|
135
|
+
ncclDataType_t dataType, ncclRedOp_t redOp, void* sendMhandle, void* recvMhandle, void** request);
|
|
136
|
+
ncclResult_t (*iallgather)(void* collComm, void* sendData, int nRecvParts, ncclNetSGE_v8_t* recvParts,
|
|
137
|
+
size_t bytesPerRank, size_t windowOffset, size_t windowBytes,
|
|
138
|
+
void* sendMhandle, void** request);
|
|
139
|
+
ncclResult_t (*ireducescatter)(void* collComm, int nSendParts, ncclNetSGE_v8_t* sendParts, void* recvData,
|
|
140
|
+
size_t bytesPerRank, size_t windowOffset, size_t windowBytes,
|
|
141
|
+
ncclDataType_t dataType, ncclRedOp_t redOp,
|
|
142
|
+
void* recvMhandle, void** request);
|
|
143
|
+
// Perform a flush/fence to make sure all data received with NCCL_PTR_CUDA is
|
|
144
|
+
// visible to the GPU
|
|
145
|
+
ncclResult_t (*iflush)(void* collComm, void* data, int size, void* mhandle, void** request);
|
|
146
|
+
// Test whether a request is complete. If size is not NULL, it returns the
|
|
147
|
+
// number of bytes sent/received.
|
|
148
|
+
ncclResult_t (*test)(void* request, int* done, int* size);
|
|
149
|
+
// Close and free collective comm objects
|
|
150
|
+
ncclResult_t (*closeColl)(void* collComm);
|
|
151
|
+
ncclResult_t (*closeListen)(void* listenComm);
|
|
152
|
+
} ncclCollNet_v8_t;
|
|
153
|
+
|
|
154
|
+
typedef ncclCollNet_v8_t ncclCollNet_t;
|
|
155
|
+
|
|
156
|
+
#define NCCL_COLLNET_PLUGIN_SYMBOL ncclCollNetPlugin_v8
|
|
157
|
+
|
|
158
|
+
typedef struct {
|
|
159
|
+
char* name; // Used mostly for logging.
|
|
160
|
+
char* pciPath; // Path to the PCI device in /sys.
|
|
161
|
+
uint64_t guid; // Unique identifier for the NIC chip. Important for
|
|
162
|
+
// cards with multiple PCI functions (Physical or virtual).
|
|
163
|
+
int ptrSupport; // [NCCL_PTR_HOST|NCCL_PTR_CUDA|NCCL_PTR_DMABUF]
|
|
164
|
+
int speed; // Port speed in Mbps.
|
|
165
|
+
int port; // Port number.
|
|
166
|
+
float latency; // Network latency
|
|
167
|
+
int maxComms; // Maximum number of comms we can create
|
|
168
|
+
int maxRecvs; // Maximum number of grouped receives.
|
|
169
|
+
ncclNetDeviceType netDeviceType; // Network offload type
|
|
170
|
+
int netDeviceVersion; // Version number for network offload
|
|
171
|
+
} ncclNetProperties_v7_t;
|
|
172
|
+
|
|
173
|
+
typedef struct {
|
|
174
|
+
// Name of the network (mainly for logs)
|
|
175
|
+
const char* name;
|
|
176
|
+
// Initialize the network.
|
|
177
|
+
ncclResult_t (*init)(ncclDebugLogger_t logFunction);
|
|
178
|
+
// Return the number of adapters.
|
|
179
|
+
ncclResult_t (*devices)(int* ndev);
|
|
180
|
+
// Get various device properties.
|
|
181
|
+
ncclResult_t (*getProperties)(int dev, ncclNetProperties_v7_t* props);
|
|
182
|
+
// Create a receiving object and provide a handle to connect to it. The
|
|
183
|
+
// handle can be up to NCCL_NET_HANDLE_MAXSIZE bytes and will be exchanged
|
|
184
|
+
// between ranks to create a connection.
|
|
185
|
+
ncclResult_t (*listen)(int dev, void* handle, void** listenComm);
|
|
186
|
+
// Connect to a handle and return a sending comm object for that peer.
|
|
187
|
+
// This call must not block for the connection to be established, and instead
|
|
188
|
+
// should return successfully with sendComm == NULL with the expectation that
|
|
189
|
+
// it will be called again until sendComm != NULL.
|
|
190
|
+
// If *sendDevComm points to a valid object, then NCCL is requesting device offload for this connection
|
|
191
|
+
ncclResult_t (*connect)(int dev, void* handle, void** sendComm, ncclNetDeviceHandle_v7_t** sendDevComm);
|
|
192
|
+
// Finalize connection establishment after remote peer has called connect.
|
|
193
|
+
// This call must not block for the connection to be established, and instead
|
|
194
|
+
// should return successfully with recvComm == NULL with the expectation that
|
|
195
|
+
// it will be called again until recvComm != NULL.
|
|
196
|
+
// If *recvDevComm points to a valid object, then NCCL is requesting device offload for this connection
|
|
197
|
+
ncclResult_t (*accept)(void* listenComm, void** recvComm, ncclNetDeviceHandle_v7_t** recvDevComm);
|
|
198
|
+
// Register/Deregister memory. Comm can be either a sendComm or a recvComm.
|
|
199
|
+
// Type is either NCCL_PTR_HOST or NCCL_PTR_CUDA.
|
|
200
|
+
ncclResult_t (*regMr)(void* comm, void* data, int size, int type, void** mhandle);
|
|
201
|
+
/* DMA-BUF support */
|
|
202
|
+
ncclResult_t (*regMrDmaBuf)(void* comm, void* data, size_t size, int type, uint64_t offset, int fd, void** mhandle);
|
|
203
|
+
ncclResult_t (*deregMr)(void* comm, void* mhandle);
|
|
204
|
+
// Asynchronous send to a peer.
|
|
205
|
+
// May return request == NULL if the call cannot be performed (or would block)
|
|
206
|
+
ncclResult_t (*isend)(void* sendComm, void* data, int size, int tag, void* mhandle, void** request);
|
|
207
|
+
// Asynchronous recv from a peer.
|
|
208
|
+
// May return request == NULL if the call cannot be performed (or would block)
|
|
209
|
+
ncclResult_t (*irecv)(void* recvComm, int n, void** data, int* sizes, int* tags, void** mhandles, void** request);
|
|
210
|
+
// Perform a flush/fence to make sure all data received with NCCL_PTR_CUDA is
|
|
211
|
+
// visible to the GPU
|
|
212
|
+
ncclResult_t (*iflush)(void* recvComm, int n, void** data, int* sizes, void** mhandles, void** request);
|
|
213
|
+
// Test whether a request is complete. If size is not NULL, it returns the
|
|
214
|
+
// number of bytes sent/received.
|
|
215
|
+
ncclResult_t (*test)(void* request, int* done, int* sizes);
|
|
216
|
+
// Close and free send/recv comm objects
|
|
217
|
+
ncclResult_t (*closeSend)(void* sendComm);
|
|
218
|
+
ncclResult_t (*closeRecv)(void* recvComm);
|
|
219
|
+
ncclResult_t (*closeListen)(void* listenComm);
|
|
220
|
+
|
|
221
|
+
// Copy the given mhandle to a dptr in a format usable by this plugin's device code
|
|
222
|
+
ncclResult_t (*getDeviceMr)(void* comm, void* mhandle, void** dptr_mhandle);
|
|
223
|
+
|
|
224
|
+
// Notify the plugin that a recv has completed by the device
|
|
225
|
+
ncclResult_t (*irecvConsumed)(void* recvComm, int n, void* request);
|
|
226
|
+
} ncclNet_v7_t;
|
|
227
|
+
|
|
228
|
+
typedef struct {
|
|
229
|
+
// Name of the collective network (mainly for logs)
|
|
230
|
+
const char* name;
|
|
231
|
+
// Initialize the collective network.
|
|
232
|
+
ncclResult_t (*init)(ncclDebugLogger_t logFunction);
|
|
233
|
+
// Return the number of adapters capable of doing collective operations.
|
|
234
|
+
// If ndev returns 0, all other functions might be set to NULL.
|
|
235
|
+
ncclResult_t (*devices)(int* ndev);
|
|
236
|
+
// Get various device properties.
|
|
237
|
+
ncclResult_t (*getProperties)(int dev, ncclNetProperties_v7_t* props);
|
|
238
|
+
// Create a receiving object and provide a handle to connect to it. The
|
|
239
|
+
// handle can be up to NCCL_NET_HANDLE_MAXSIZE bytes and will be exchanged
|
|
240
|
+
// between ranks to create connections.
|
|
241
|
+
ncclResult_t (*listen)(int dev, void* handle, void** listenComm);
|
|
242
|
+
// Create a group for collective operations. handles have been created
|
|
243
|
+
// using listen() above. rank indicates caller's rank in the collective network.
|
|
244
|
+
ncclResult_t (*connect)(void* handles[], int nranks, int rank, void* listenComm, void** collComm);
|
|
245
|
+
// Returns whether a reduction operation on a data type is supported.
|
|
246
|
+
// 1 for supported, 0 otherwise.
|
|
247
|
+
ncclResult_t (*reduceSupport)(ncclDataType_t dataType, ncclRedOp_t redOp, int* supported);
|
|
248
|
+
// Register/Deregister memory. Type is either NCCL_PTR_HOST or NCCL_PTR_CUDA.
|
|
249
|
+
ncclResult_t (*regMr)(void* collComm, void* data, int size, int type, void** mhandle);
|
|
250
|
+
/* DMA-BUF support */
|
|
251
|
+
ncclResult_t (*regMrDmaBuf)(void* collComm, void* data, size_t size, int type, uint64_t offset, int fd, void** mhandle);
|
|
252
|
+
ncclResult_t (*deregMr)(void* collComm, void* mhandle);
|
|
253
|
+
// Performs an asynchronous allreduce operation on the collective group.
|
|
254
|
+
// May return request == NULL if the call cannot be performed (or would block).
|
|
255
|
+
ncclResult_t (*iallreduce)(void* collComm, void* sendData, void* recvData, int count,
|
|
256
|
+
ncclDataType_t dataType, ncclRedOp_t redOp, void* sendMhandle, void* recvMhandle, void** request);
|
|
257
|
+
// Perform a flush/fence to make sure all data received with NCCL_PTR_CUDA is
|
|
258
|
+
// visible to the GPU
|
|
259
|
+
ncclResult_t (*iflush)(void* collComm, void* data, int size, void* mhandle, void** request);
|
|
260
|
+
// Test whether a request is complete. If size is not NULL, it returns the
|
|
261
|
+
// number of bytes sent/received.
|
|
262
|
+
ncclResult_t (*test)(void* request, int* done, int* size);
|
|
263
|
+
// Close and free collective comm objects
|
|
264
|
+
ncclResult_t (*closeColl)(void* collComm);
|
|
265
|
+
ncclResult_t (*closeListen)(void* listenComm);
|
|
266
|
+
} ncclCollNet_v7_t;
|
|
267
|
+
|
|
268
|
+
#define NCCL_NET_MAX_REQUESTS_V6 8
|
|
269
|
+
|
|
270
|
+
// v6 struct for backwards compatibility
|
|
271
|
+
typedef struct {
|
|
272
|
+
char* name; // Used mostly for logging.
|
|
273
|
+
char* pciPath; // Path to the PCI device in /sys.
|
|
274
|
+
uint64_t guid; // Unique identifier for the NIC chip. Important for
|
|
275
|
+
// cards with multiple PCI functions (Physical or virtual).
|
|
276
|
+
int ptrSupport; // [NCCL_PTR_HOST|NCCL_PTR_CUDA|NCCL_PTR_DMABUF]
|
|
277
|
+
int speed; // Port speed in Mbps.
|
|
278
|
+
int port; // Port number.
|
|
279
|
+
float latency; // Network latency
|
|
280
|
+
int maxComms; // Maximum number of comms we can create
|
|
281
|
+
int maxRecvs; // Maximum number of grouped receives.
|
|
282
|
+
} ncclNetProperties_v6_t;
|
|
283
|
+
|
|
284
|
+
typedef struct {
|
|
285
|
+
// Name of the network (mainly for logs)
|
|
286
|
+
const char* name;
|
|
287
|
+
// Initialize the network.
|
|
288
|
+
ncclResult_t (*init)(ncclDebugLogger_t logFunction);
|
|
289
|
+
// Return the number of adapters.
|
|
290
|
+
ncclResult_t (*devices)(int* ndev);
|
|
291
|
+
// Get various device properties.
|
|
292
|
+
ncclResult_t (*getProperties)(int dev, ncclNetProperties_v6_t* props);
|
|
293
|
+
// Create a receiving object and provide a handle to connect to it. The
|
|
294
|
+
// handle can be up to NCCL_NET_HANDLE_MAXSIZE bytes and will be exchanged
|
|
295
|
+
// between ranks to create a connection.
|
|
296
|
+
ncclResult_t (*listen)(int dev, void* handle, void** listenComm);
|
|
297
|
+
// Connect to a handle and return a sending comm object for that peer.
|
|
298
|
+
// This call must not block for the connection to be established, and instead
|
|
299
|
+
// should return successfully with sendComm == NULL with the expectation that
|
|
300
|
+
// it will be called again until sendComm != NULL.
|
|
301
|
+
ncclResult_t (*connect)(int dev, void* handle, void** sendComm);
|
|
302
|
+
// Finalize connection establishment after remote peer has called connect.
|
|
303
|
+
// This call must not block for the connection to be established, and instead
|
|
304
|
+
// should return successfully with recvComm == NULL with the expectation that
|
|
305
|
+
// it will be called again until recvComm != NULL.
|
|
306
|
+
ncclResult_t (*accept)(void* listenComm, void** recvComm);
|
|
307
|
+
// Register/Deregister memory. Comm can be either a sendComm or a recvComm.
|
|
308
|
+
// Type is either NCCL_PTR_HOST or NCCL_PTR_CUDA.
|
|
309
|
+
ncclResult_t (*regMr)(void* comm, void* data, int size, int type, void** mhandle);
|
|
310
|
+
/* DMA-BUF support */
|
|
311
|
+
ncclResult_t (*regMrDmaBuf)(void* comm, void* data, size_t size, int type, uint64_t offset, int fd, void** mhandle);
|
|
312
|
+
ncclResult_t (*deregMr)(void* comm, void* mhandle);
|
|
313
|
+
// Asynchronous send to a peer.
|
|
314
|
+
// May return request == NULL if the call cannot be performed (or would block)
|
|
315
|
+
ncclResult_t (*isend)(void* sendComm, void* data, int size, int tag, void* mhandle, void** request);
|
|
316
|
+
// Asynchronous recv from a peer.
|
|
317
|
+
// May return request == NULL if the call cannot be performed (or would block)
|
|
318
|
+
ncclResult_t (*irecv)(void* recvComm, int n, void** data, int* sizes, int* tags, void** mhandles, void** request);
|
|
319
|
+
// Perform a flush/fence to make sure all data received with NCCL_PTR_CUDA is
|
|
320
|
+
// visible to the GPU
|
|
321
|
+
ncclResult_t (*iflush)(void* recvComm, int n, void** data, int* sizes, void** mhandles, void** request);
|
|
322
|
+
// Test whether a request is complete. If size is not NULL, it returns the
|
|
323
|
+
// number of bytes sent/received.
|
|
324
|
+
ncclResult_t (*test)(void* request, int* done, int* sizes);
|
|
325
|
+
// Close and free send/recv comm objects
|
|
326
|
+
ncclResult_t (*closeSend)(void* sendComm);
|
|
327
|
+
ncclResult_t (*closeRecv)(void* recvComm);
|
|
328
|
+
ncclResult_t (*closeListen)(void* listenComm);
|
|
329
|
+
} ncclNet_v6_t;
|
|
330
|
+
|
|
331
|
+
typedef struct {
|
|
332
|
+
// Name of the collective network (mainly for logs)
|
|
333
|
+
const char* name;
|
|
334
|
+
// Initialize the collective network.
|
|
335
|
+
ncclResult_t (*init)(ncclDebugLogger_t logFunction);
|
|
336
|
+
// Return the number of adapters capable of doing collective operations.
|
|
337
|
+
// If ndev returns 0, all other functions might be set to NULL.
|
|
338
|
+
ncclResult_t (*devices)(int* ndev);
|
|
339
|
+
// Get various device properties.
|
|
340
|
+
ncclResult_t (*getProperties)(int dev, ncclNetProperties_v6_t* props);
|
|
341
|
+
// Create a receiving object and provide a handle to connect to it. The
|
|
342
|
+
// handle can be up to NCCL_NET_HANDLE_MAXSIZE bytes and will be exchanged
|
|
343
|
+
// between ranks to create connections.
|
|
344
|
+
ncclResult_t (*listen)(int dev, void* handle, void** listenComm);
|
|
345
|
+
// Create a group for collective operations. handles have been created
|
|
346
|
+
// using listen() above. rank indicates caller's rank in the collective network.
|
|
347
|
+
ncclResult_t (*connect)(void* handles[], int nranks, int rank, void* listenComm, void** collComm);
|
|
348
|
+
// Returns whether a reduction operation on a data type is supported.
|
|
349
|
+
// 1 for supported, 0 otherwise.
|
|
350
|
+
ncclResult_t (*reduceSupport)(ncclDataType_t dataType, ncclRedOp_t redOp, int* supported);
|
|
351
|
+
// Register/Deregister memory. Type is either NCCL_PTR_HOST or NCCL_PTR_CUDA.
|
|
352
|
+
ncclResult_t (*regMr)(void* collComm, void* data, int size, int type, void** mhandle);
|
|
353
|
+
/* DMA-BUF support */
|
|
354
|
+
ncclResult_t (*regMrDmaBuf)(void* collComm, void* data, size_t size, int type, uint64_t offset, int fd, void** mhandle);
|
|
355
|
+
ncclResult_t (*deregMr)(void* collComm, void* mhandle);
|
|
356
|
+
// Performs an asynchronous allreduce operation on the collective group.
|
|
357
|
+
// May return request == NULL if the call cannot be performed (or would block).
|
|
358
|
+
ncclResult_t (*iallreduce)(void* collComm, void* sendData, void* recvData, int count,
|
|
359
|
+
ncclDataType_t dataType, ncclRedOp_t redOp, void* sendMhandle, void* recvMhandle, void** request);
|
|
360
|
+
// Perform a flush/fence to make sure all data received with NCCL_PTR_CUDA is
|
|
361
|
+
// visible to the GPU
|
|
362
|
+
ncclResult_t (*iflush)(void* collComm, void* data, int size, void* mhandle, void** request);
|
|
363
|
+
// Test whether a request is complete. If size is not NULL, it returns the
|
|
364
|
+
// number of bytes sent/received.
|
|
365
|
+
ncclResult_t (*test)(void* request, int* done, int* size);
|
|
366
|
+
// Close and free collective comm objects
|
|
367
|
+
ncclResult_t (*closeColl)(void* collComm);
|
|
368
|
+
ncclResult_t (*closeListen)(void* listenComm);
|
|
369
|
+
} ncclCollNet_v6_t;
|
|
370
|
+
|
|
371
|
+
// v5 struct for backwards compatibility
|
|
372
|
+
typedef struct {
|
|
373
|
+
// Name of the network (mainly for logs)
|
|
374
|
+
const char* name;
|
|
375
|
+
// Initialize the network.
|
|
376
|
+
ncclResult_t (*init)(ncclDebugLogger_t logFunction);
|
|
377
|
+
// Return the number of adapters.
|
|
378
|
+
ncclResult_t (*devices)(int* ndev);
|
|
379
|
+
// Get various device properties.
|
|
380
|
+
ncclResult_t (*getProperties)(int dev, ncclNetProperties_v6_t* props);
|
|
381
|
+
// Create a receiving object and provide a handle to connect to it. The
|
|
382
|
+
// handle can be up to NCCL_NET_HANDLE_MAXSIZE bytes and will be exchanged
|
|
383
|
+
// between ranks to create a connection.
|
|
384
|
+
ncclResult_t (*listen)(int dev, void* handle, void** listenComm);
|
|
385
|
+
// Connect to a handle and return a sending comm object for that peer.
|
|
386
|
+
// This call must not block for the connection to be established, and instead
|
|
387
|
+
// should return successfully with sendComm == NULL with the expectation that
|
|
388
|
+
// it will be called again until sendComm != NULL.
|
|
389
|
+
ncclResult_t (*connect)(int dev, void* handle, void** sendComm);
|
|
390
|
+
// Finalize connection establishment after remote peer has called connect.
|
|
391
|
+
// This call must not block for the connection to be established, and instead
|
|
392
|
+
// should return successfully with recvComm == NULL with the expectation that
|
|
393
|
+
// it will be called again until recvComm != NULL.
|
|
394
|
+
ncclResult_t (*accept)(void* listenComm, void** recvComm);
|
|
395
|
+
// Register/Deregister memory. Comm can be either a sendComm or a recvComm.
|
|
396
|
+
// Type is either NCCL_PTR_HOST or NCCL_PTR_CUDA.
|
|
397
|
+
ncclResult_t (*regMr)(void* comm, void* data, int size, int type, void** mhandle);
|
|
398
|
+
ncclResult_t (*deregMr)(void* comm, void* mhandle);
|
|
399
|
+
// Asynchronous send to a peer.
|
|
400
|
+
// May return request == NULL if the call cannot be performed (or would block)
|
|
401
|
+
ncclResult_t (*isend)(void* sendComm, void* data, int size, int tag, void* mhandle, void** request);
|
|
402
|
+
// Asynchronous recv from a peer.
|
|
403
|
+
// May return request == NULL if the call cannot be performed (or would block)
|
|
404
|
+
ncclResult_t (*irecv)(void* recvComm, int n, void** data, int* sizes, int* tags, void** mhandles, void** request);
|
|
405
|
+
// Perform a flush/fence to make sure all data received with NCCL_PTR_CUDA is
|
|
406
|
+
// visible to the GPU
|
|
407
|
+
ncclResult_t (*iflush)(void* recvComm, int n, void** data, int* sizes, void** mhandles, void** request);
|
|
408
|
+
// Test whether a request is complete. If size is not NULL, it returns the
|
|
409
|
+
// number of bytes sent/received.
|
|
410
|
+
ncclResult_t (*test)(void* request, int* done, int* sizes);
|
|
411
|
+
// Close and free send/recv comm objects
|
|
412
|
+
ncclResult_t (*closeSend)(void* sendComm);
|
|
413
|
+
ncclResult_t (*closeRecv)(void* recvComm);
|
|
414
|
+
ncclResult_t (*closeListen)(void* listenComm);
|
|
415
|
+
} ncclNet_v5_t;
|
|
416
|
+
|
|
417
|
+
// v5 struct for backwards compatibility
|
|
418
|
+
typedef struct {
|
|
419
|
+
// Name of the collective network (mainly for logs)
|
|
420
|
+
const char* name;
|
|
421
|
+
// Initialize the collective network.
|
|
422
|
+
ncclResult_t (*init)(ncclDebugLogger_t logFunction);
|
|
423
|
+
// Return the number of adapters capable of doing collective operations.
|
|
424
|
+
// If ndev returns 0, all other functions might be set to NULL.
|
|
425
|
+
ncclResult_t (*devices)(int* ndev);
|
|
426
|
+
// Get various device properties.
|
|
427
|
+
ncclResult_t (*getProperties)(int dev, ncclNetProperties_v6_t* props);
|
|
428
|
+
// Create a receiving object and provide a handle to connect to it. The
|
|
429
|
+
// handle can be up to NCCL_NET_HANDLE_MAXSIZE bytes and will be exchanged
|
|
430
|
+
// between ranks to create connections.
|
|
431
|
+
ncclResult_t (*listen)(int dev, void* handle, void** listenComm);
|
|
432
|
+
// Create a group for collective operations. handles have been created
|
|
433
|
+
// using listen() above. rank indicates caller's rank in the collective network.
|
|
434
|
+
ncclResult_t (*connect)(void* handles[], int nranks, int rank, void* listenComm, void** collComm);
|
|
435
|
+
// Returns whether a reduction operation on a data type is supported.
|
|
436
|
+
// 1 for supported, 0 otherwise.
|
|
437
|
+
ncclResult_t (*reduceSupport)(ncclDataType_t dataType, ncclRedOp_t redOp, int* supported);
|
|
438
|
+
// Register/Deregister memory. Type is either NCCL_PTR_HOST or NCCL_PTR_CUDA.
|
|
439
|
+
ncclResult_t (*regMr)(void* collComm, void* data, int size, int type, void** mhandle);
|
|
440
|
+
ncclResult_t (*deregMr)(void* collComm, void* mhandle);
|
|
441
|
+
// Performs an asynchronous allreduce operation on the collective group.
|
|
442
|
+
// May return request == NULL if the call cannot be performed (or would block).
|
|
443
|
+
ncclResult_t (*iallreduce)(void* collComm, void* sendData, void* recvData, int count,
|
|
444
|
+
ncclDataType_t dataType, ncclRedOp_t redOp, void* sendMhandle, void* recvMhandle, void** request);
|
|
445
|
+
// Perform a flush/fence to make sure all data received with NCCL_PTR_CUDA is
|
|
446
|
+
// visible to the GPU
|
|
447
|
+
ncclResult_t (*iflush)(void* collComm, void* data, int size, void* mhandle, void** request);
|
|
448
|
+
// Test whether a request is complete. If size is not NULL, it returns the
|
|
449
|
+
// number of bytes sent/received.
|
|
450
|
+
ncclResult_t (*test)(void* request, int* done, int* size);
|
|
451
|
+
// Close and free collective comm objects
|
|
452
|
+
ncclResult_t (*closeColl)(void* collComm);
|
|
453
|
+
ncclResult_t (*closeListen)(void* listenComm);
|
|
454
|
+
} ncclCollNet_v5_t;
|
|
455
|
+
|
|
456
|
+
#endif // end include guard
|
|
File without changes
|
|
Binary file
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
|
|
2
|
+
Copyright (c) 2015-2019, NVIDIA CORPORATION. All rights reserved.
|
|
3
|
+
|
|
4
|
+
Redistribution and use in source and binary forms, with or without
|
|
5
|
+
modification, are permitted provided that the following conditions
|
|
6
|
+
are met:
|
|
7
|
+
* Redistributions of source code must retain the above copyright
|
|
8
|
+
notice, this list of conditions and the following disclaimer.
|
|
9
|
+
* Redistributions in binary form must reproduce the above copyright
|
|
10
|
+
notice, this list of conditions and the following disclaimer in the
|
|
11
|
+
documentation and/or other materials provided with the distribution.
|
|
12
|
+
* Neither the name of NVIDIA CORPORATION, Lawrence Berkeley National
|
|
13
|
+
Laboratory, the U.S. Department of Energy, nor the names of their
|
|
14
|
+
contributors may be used to endorse or promote products derived
|
|
15
|
+
from this software without specific prior written permission.
|
|
16
|
+
|
|
17
|
+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ``AS IS'' AND ANY
|
|
18
|
+
EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
|
19
|
+
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
|
20
|
+
PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
|
|
21
|
+
CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
|
22
|
+
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
|
|
23
|
+
PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
|
|
24
|
+
PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
|
|
25
|
+
OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
26
|
+
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
|
27
|
+
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
28
|
+
|
|
29
|
+
The U.S. Department of Energy funded the development of this software
|
|
30
|
+
under subcontract 7078610 with Lawrence Berkeley National Laboratory.
|
|
31
|
+
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
Metadata-Version: 2.1
|
|
2
|
+
Name: nvidia-nccl-cu12
|
|
3
|
+
Version: 2.20.3
|
|
4
|
+
Summary: NVIDIA Collective Communication Library (NCCL) Runtime
|
|
5
|
+
Home-page: https://developer.nvidia.com/cuda-zone
|
|
6
|
+
Author: Nvidia CUDA Installer Team
|
|
7
|
+
Author-email: cuda_installer@nvidia.com
|
|
8
|
+
License: NVIDIA Proprietary Software
|
|
9
|
+
Keywords: cuda,nvidia,runtime,machine learning,deep learning
|
|
10
|
+
Classifier: Development Status :: 4 - Beta
|
|
11
|
+
Classifier: Intended Audience :: Developers
|
|
12
|
+
Classifier: Intended Audience :: Education
|
|
13
|
+
Classifier: Intended Audience :: Science/Research
|
|
14
|
+
Classifier: License :: Other/Proprietary License
|
|
15
|
+
Classifier: Natural Language :: English
|
|
16
|
+
Classifier: Programming Language :: Python :: 3
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.5
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.6
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.7
|
|
20
|
+
Classifier: Programming Language :: Python :: 3.8
|
|
21
|
+
Classifier: Programming Language :: Python :: 3.9
|
|
22
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
23
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
24
|
+
Classifier: Programming Language :: Python :: 3 :: Only
|
|
25
|
+
Classifier: Topic :: Scientific/Engineering
|
|
26
|
+
Classifier: Topic :: Scientific/Engineering :: Mathematics
|
|
27
|
+
Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence
|
|
28
|
+
Classifier: Topic :: Software Development
|
|
29
|
+
Classifier: Topic :: Software Development :: Libraries
|
|
30
|
+
Classifier: Operating System :: Microsoft :: Windows
|
|
31
|
+
Classifier: Operating System :: POSIX :: Linux
|
|
32
|
+
Requires-Python: >=3
|
|
33
|
+
License-File: License.txt
|
|
34
|
+
|
|
35
|
+
NCCL (pronounced "Nickel") is a stand-alone library of standard collective communication routines for GPUs, implementing all-reduce, all-gather, reduce, broadcast, and reduce-scatter. It has been optimized to achieve high bandwidth on any platform using PCIe, NVLink, NVswitch, as well as networking using InfiniBand Verbs or TCP/IP sockets.
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
nvidia/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
2
|
+
nvidia/nccl/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
3
|
+
nvidia/nccl/include/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
4
|
+
nvidia/nccl/include/nccl.h,sha256=hXFU1TBJE-XskPiCxc6Tyz5nmw13euDTPFuoSwXB7KU,19004
|
|
5
|
+
nvidia/nccl/include/nccl_net.h,sha256=Q2yMEZBE6uKkX_nduRb3TaU64hC1jjOMstCypTKGSdk,25896
|
|
6
|
+
nvidia/nccl/lib/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
7
|
+
nvidia/nccl/lib/libnccl.so.2,sha256=PD3Jh11X4sZwIy8gScG9BrVsXSuW3k6NDMk8n6pRZ-Q,233067008
|
|
8
|
+
nvidia_nccl_cu12-2.20.3.dist-info/License.txt,sha256=92n6LTYyE_WZNm2kbiqNZQyG6q6EWuxNRLL1_QHU7Fk,1735
|
|
9
|
+
nvidia_nccl_cu12-2.20.3.dist-info/METADATA,sha256=R5PWgWE7Pv2_O5O4LY0lw813dY4lw8COlGHBSg88YhU,1834
|
|
10
|
+
nvidia_nccl_cu12-2.20.3.dist-info/WHEEL,sha256=9CRMXDorwIsYQ7oMclfPm08dJYUjgkXikOwZLcFAjsA,110
|
|
11
|
+
nvidia_nccl_cu12-2.20.3.dist-info/top_level.txt,sha256=fTkAtiFuL16nUrB9ytDDtpytz2t0B4NvYTnRzwAhO14,7
|
|
12
|
+
nvidia_nccl_cu12-2.20.3.dist-info/RECORD,,
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
nvidia
|