Coverage for cuda / core / _memory / _memory_pool.pyx: 86.92%
107 statements
« prev ^ index » next coverage.py v7.13.5, created at 2026-04-29 01:27 +0000
« prev ^ index » next coverage.py v7.13.5, created at 2026-04-29 01:27 +0000
1# SPDX-FileCopyrightText: Copyright (c) 2024-2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
2#
3# SPDX-License-Identifier: Apache-2.0
5from __future__ import annotations
7from libc.limits cimport ULLONG_MAX
8from libc.stdint cimport uintptr_t
9from libc.string cimport memset
11from cuda.bindings cimport cydriver
12from cuda.core._memory._buffer cimport Buffer, Buffer_from_deviceptr_handle, MemoryResource
13from cuda.core._memory cimport _ipc
14from cuda.core._stream cimport default_stream, Stream_accept, Stream
15from cuda.core._resource_handles cimport (
16 MemoryPoolHandle,
17 DevicePtrHandle,
18 create_mempool_handle,
19 deviceptr_alloc_from_pool,
20 as_cu,
21 as_py,
22)
23from cuda.core._resource_handles cimport create_mempool_handle_ref # no-cython-lint
25from cuda.core._utils.cuda_utils cimport (
26 HANDLE_RETURN,
27)
30cdef class _MemPoolAttributes:
31 """Provides access to memory pool attributes."""
33 def __init__(self, *args, **kwargs):
34 raise RuntimeError("_MemPoolAttributes cannot be instantiated directly. Please use MemoryResource APIs.")
36 @staticmethod
37 cdef _MemPoolAttributes _init(MemoryPoolHandle h_pool):
38 cdef _MemPoolAttributes self = _MemPoolAttributes.__new__(_MemPoolAttributes) 18XjfRN9Y!Z#0kgSOEdoFGHep$1lhTP%2'3(4miUQLnMbac
39 self._h_pool = h_pool 18XjfRN9Y!Z#0kgSOEdoFGHep$1lhTP%2'3(4miUQLnMbac
40 return self 18XjfRN9Y!Z#0kgSOEdoFGHep$1lhTP%2'3(4miUQLnMbac
42 def __repr__(self):
43 return f"{self.__class__.__name__}(%s)" % ", ".join( 1bac
44 f"{attr}={getattr(self, attr)}" for attr in dir(self) 1bac
45 if not attr.startswith("_") 1bac
46 )
48 cdef int _getattribute(self, cydriver.CUmemPool_attribute attr_enum, void* value) except?-1:
49 with nogil: 18XjfRN9Y!Z#0kgSOEdoFGHep$1lhTP%2'3(4miUQLnMbac
50 HANDLE_RETURN(cydriver.cuMemPoolGetAttribute(as_cu(self._h_pool), attr_enum, value)) 18XjfRN9Y!Z#0kgSOEdoFGHep$1lhTP%2'3(4miUQLnMbac
51 return 0 18XjfRN9Y!Z#0kgSOEdoFGHep$1lhTP%2'3(4miUQLnMbac
53 @property
54 def reuse_follow_event_dependencies(self):
55 """Allow memory to be reused when there are event dependencies between streams."""
56 cdef int value
57 self._getattribute(cydriver.CUmemPool_attribute.CU_MEMPOOL_ATTR_REUSE_FOLLOW_EVENT_DEPENDENCIES, &value) 1#0H(4bac
58 return bool(value) 1#0H(4bac
60 @property
61 def reuse_allow_opportunistic(self):
62 """Allow reuse of completed frees without dependencies."""
63 cdef int value
64 self._getattribute(cydriver.CUmemPool_attribute.CU_MEMPOOL_ATTR_REUSE_ALLOW_OPPORTUNISTIC, &value) 1!ZG'3bac
65 return bool(value) 1!ZG'3bac
67 @property
68 def reuse_allow_internal_dependencies(self):
69 """Allow insertion of new stream dependencies for memory reuse."""
70 cdef int value
71 self._getattribute(cydriver.CUmemPool_attribute.CU_MEMPOOL_ATTR_REUSE_ALLOW_INTERNAL_DEPENDENCIES, &value) 19YF%2bac
72 return bool(value) 19YF%2bac
74 @property
75 def release_threshold(self):
76 """Amount of reserved memory to hold before OS release."""
77 cdef cydriver.cuuint64_t value
78 self._getattribute(cydriver.CUmemPool_attribute.CU_MEMPOOL_ATTR_RELEASE_THRESHOLD, &value) 18XE$1bac
79 return int(value) 18XE$1bac
81 @property
82 def reserved_mem_current(self):
83 """Current amount of backing memory allocated."""
84 cdef cydriver.cuuint64_t value
85 self._getattribute(cydriver.CUmemPool_attribute.CU_MEMPOOL_ATTR_RESERVED_MEM_CURRENT, &value) 1jfRNdolhTPbac
86 return int(value) 1jfRNdolhTPbac
88 @property
89 def reserved_mem_high(self):
90 """High watermark of backing memory allocated."""
91 cdef cydriver.cuuint64_t value
92 self._getattribute(cydriver.CUmemPool_attribute.CU_MEMPOOL_ATTR_RESERVED_MEM_HIGH, &value) 1RNoTPbac
93 return int(value) 1RNoTPbac
95 @property
96 def used_mem_current(self):
97 """Current amount of memory in use."""
98 cdef cydriver.cuuint64_t value
99 self._getattribute(cydriver.CUmemPool_attribute.CU_MEMPOOL_ATTR_USED_MEM_CURRENT, &value) 1kgSOepmiUQbac
100 return int(value) 1kgSOepmiUQbac
102 @property
103 def used_mem_high(self):
104 """High watermark of memory in use."""
105 cdef cydriver.cuuint64_t value
106 self._getattribute(cydriver.CUmemPool_attribute.CU_MEMPOOL_ATTR_USED_MEM_HIGH, &value) 1SOpUQLnMbac
107 return int(value) 1SOpUQLnMbac
110cdef class _MemPool(MemoryResource):
112 def __cinit__(self):
113 # Note: subclasses use MP_init_create_pool or MP_init_current_pool to initialize.
114 self._mempool_owned = False 2. / : } ~ abbbcbdbebfbgchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t gbhbibjb; = 5 ydI zd? Ad@ [ ] BdC kbJ ^ 8 X j f R N 9 Y ! Z # 0 k g S O E Cdd Ddo EdF FdG GdH Hde Idp Jd$ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 lb_ ` 7 D K mb{ ) benb* + , - obpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.b/b:b;b=b?b@b[b]b^b_b`b{b|b}b~bacbcccdcecfc
115 self._ipc_data = None 28c. / : } ~ abbbcbdbebfbgchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t gbhbibjb; = 5 ydI zd? Ad@ [ ] BdC kbJ ^ 8 X j f R N 9 Y ! Z # 0 k g S O E Cdd Ddo EdF FdG GdH Hde Idp Jd$ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 lb_ ` 7 D K mb{ ) benb* + , - obpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.b/b:b;b=b?b@b[b]b^b_b`b{b|b}b~bacbcccdcecfc
116 self._attributes = None 2. / : } ~ abbbcbdbebfbgchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t gbhbibjb; = 5 ydI zd? Ad@ [ ] BdC kbJ ^ 8 X j f R N 9 Y ! Z # 0 k g S O E Cdd Ddo EdF FdG GdH Hde Idp Jd$ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 lb_ ` 7 D K mb{ ) benb* + , - obpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.b/b:b;b=b?b@b[b]b^b_b`b{b|b}b~bacbcccdcecfc
118 def close(self):
119 """
120 Close the memory resource and destroy the associated memory pool
121 if owned.
122 """
123 _MP_close(self) 2KdLdq Mdr NdOdPdu Qdv RdSdTdUdVdWdXdYdZd0d1d2d3d4d5d6d7d8d9d!d#d$d%d'd(d)d*d+d,d-d.d/d:d;d=d?d@d[d]d^d_dw x `d{d|d}d~daey z A B s t L n M D K mb{ ) * + , -
125 def allocate(self, size_t size, stream: Stream | GraphBuilder | None = None) -> Buffer:
126 """Allocate a buffer of the requested size.
128 Parameters
129 ----------
130 size : int
131 The size of the buffer to allocate, in bytes.
132 stream : :obj:`~_stream.Stream` | :obj:`~graph.GraphBuilder`, optional
133 The stream on which to perform the allocation asynchronously.
134 If None, an internal stream is used.
136 Returns
137 -------
138 Buffer
139 The allocated buffer object, which is accessible on the device that this memory
140 resource was created for.
141 """
142 if self.is_mapped: 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
143 raise TypeError("Cannot allocate from a mapped IPC-enabled memory resource")
144 stream = Stream_accept(stream) if stream is not None else default_stream() 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
145 return _MP_allocate(self, size, <Stream> stream) 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
147 def deallocate(self, ptr: "DevicePointerT", size_t size, stream: Stream | GraphBuilder | None = None):
148 """Deallocate a buffer previously allocated by this resource.
150 Parameters
151 ----------
152 ptr : :obj:`~_memory.DevicePointerT`
153 The pointer or handle to the buffer to deallocate.
154 size : int
155 The size of the buffer to deallocate, in bytes.
156 stream : :obj:`~_stream.Stream` | :obj:`~graph.GraphBuilder`, optional
157 The stream on which to perform the deallocation asynchronously.
158 If the buffer is deallocated without an explicit stream, the allocation stream
159 is used.
160 """
161 stream = Stream_accept(stream) if stream is not None else default_stream()
162 _MP_deallocate(self, <uintptr_t>ptr, size, <Stream> stream)
164 @property
165 def attributes(self) -> _MemPoolAttributes:
166 """Memory pool attributes."""
167 if self._attributes is None: 18XjfRN9Y!Z#0kgSOEdoFGHep$1lhTP%2'3(4miUQLnMbac
168 self._attributes = _MemPoolAttributes._init(self._h_pool) 18XjfRN9Y!Z#0kgSOEdoFGHep$1lhTP%2'3(4miUQLnMbac
169 return self._attributes 18XjfRN9Y!Z#0kgSOEdoFGHep$1lhTP%2'3(4miUQLnMbac
171 @property
172 def handle(self) -> object:
173 """Handle to the underlying memory pool."""
174 return as_py(self._h_pool)
176 @property
177 def is_handle_owned(self) -> bool:
178 """Whether the memory resource handle is owned. If False, ``close`` has no effect."""
179 return self._mempool_owned
181 @property
182 def is_ipc_enabled(self) -> bool:
183 """Whether this memory resource has IPC enabled."""
184 return self._ipc_data is not None 2cegcdehcq icr jc#ckc$clcu mcv nc%coc'cpc(cqc)crceescfetcgeuc*cvc+cwchexcieyc,czc-cAcjeBckeCc.cDc/cEcleFcmeGc:cHc;cIcneJcoeKc=cLc?cMcpeNcqeOc@cPc[cQcreRc]cSc^cTc_cUc`cVc{cWc|cXc}cYc~cZcad0cbd1cw x cd2cdd3ced4cfd5c9c6c!c7cy z A B s t ; = 5 C 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q 6 7 D K * + , - V W
186 @property
187 def is_mapped(self) -> bool:
188 """
189 Whether this is a mapping of an IPC-enabled memory resource from
190 another process. If True, allocation is not permitted.
191 """
192 return self._ipc_data is not None and self._ipc_data._is_mapped 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
194 @property
195 def uuid(self) -> uuid.UUID | None:
196 """
197 A universally unique identifier for this memory resource. Meaningful
198 only for IPC-enabled memory resources.
199 """
200 return getattr(self._ipc_data, 'uuid', None) 2q r 9c!cs t
203cdef int MP_init_create_pool(
204 _MemPool self,
205 cydriver.CUmemLocationType loc_type,
206 int loc_id,
207 cydriver.CUmemAllocationType alloc_type,
208 bint ipc_enabled,
209 size_t max_size,
210) except? -1:
211 """Initialize a _MemPool by creating a new memory pool with the given
212 parameters.
214 Sets ``_h_pool`` (owning), ``_mempool_owned``, and ``_ipc_data``.
215 """
216 cdef cydriver.CUmemPoolProps properties
217 memset(&properties, 0, sizeof(cydriver.CUmemPoolProps)) 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
219 properties.allocType = alloc_type 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
220 properties.handleTypes = ( 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
221 _ipc.IPC_HANDLE_TYPE if ipc_enabled 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
222 else cydriver.CUmemAllocationHandleType.CU_MEM_HANDLE_TYPE_NONE 25 I @ [ ] C J 8 j R 9 ! # k S E d o F G H e p $ l T % ' ( m U L n M b a c 6 7 K mb)
223 )
224 properties.location.id = loc_id 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
225 properties.location.type = loc_type 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
226 properties.maxSize = max_size 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
228 self._mempool_owned = True 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
229 self._h_pool = create_mempool_handle(properties) 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
231 if ipc_enabled: 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
232 alloc_handle = _ipc.MP_export_mempool(self) 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t X f N Y Z 0 g O 1 h P 2 3 4 i Q D { ) * + , - V W
233 self._ipc_data = _ipc.IPCDataForMR(alloc_handle, False) 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t X f N Y Z 0 g O 1 h P 2 3 4 i Q D { ) * + , - V W
235 return 0 2gchcq icr jckclcu mcv ncocpcqcrcsctcucvcwcxcyczcAcBcCcDcEcFcGcHcIcJcKcLcMcNcOcPcQcRcScTcUcVcWcXcYcZc0c1cw x 2c3c4c5c6c7cy z A B s t 5 I @ [ ] C J 8 X j f R N 9 Y ! Z # 0 k g S O E d o F G H e p $ 1 l h T P % 2 ' 3 ( 4 m i U Q L n M b a c 6 7 D K mb{ ) * + , - V W
238cdef int MP_init_current_pool(
239 _MemPool self,
240 cydriver.CUmemLocationType loc_type,
241 int loc_id,
242 cydriver.CUmemAllocationType alloc_type,
243) except? -1:
244 """Initialize a _MemPool by getting the driver's current pool for a
245 location and allocation type.
247 Sets ``_h_pool`` (non-owning) via ``cuMemGetMemPool``.
248 Requires CUDA 13+.
249 """
250 IF CUDA_CORE_BUILD_MAJOR >= 13:
251 cdef cydriver.CUmemLocation loc
252 cdef cydriver.CUmemoryPool pool
253 loc.id = loc_id 2ydI zd? Ad@ [ ] BdC J ^ E Cdd Ddo EdF FdG GdH Hde Idp Jdn a _ `
254 loc.type = loc_type 2ydI zd? Ad@ [ ] BdC J ^ E Cdd Ddo EdF FdG GdH Hde Idp Jdn a _ `
255 with nogil: 2ydI zd? Ad@ [ ] BdC J ^ E Cdd Ddo EdF FdG GdH Hde Idp Jdn a _ `
256 HANDLE_RETURN(cydriver.cuMemGetMemPool(&pool, &loc, alloc_type)) 2ydI zd? Ad@ [ ] BdC J ^ E Cdd Ddo EdF FdG GdH Hde Idp Jdn a _ `
257 self._h_pool = create_mempool_handle_ref(pool) 2ydI zd? Ad@ [ ] BdC J ^ E Cdd Ddo EdF FdG GdH Hde Idp Jdn a _ `
258 self._mempool_owned = False 2ydI zd? Ad@ [ ] BdC J ^ E Cdd Ddo EdF FdG GdH Hde Idp Jdn a _ `
259 ELSE:
260 raise RuntimeError(
261 "Getting the current memory pool requires CUDA 13.0 or later"
262 )
263 return 0 2ydI zd? Ad@ [ ] BdC J ^ E Cdd Ddo EdF FdG GdH Hde Idp Jdn a _ `
266cdef int MP_raise_release_threshold(_MemPool self) except? -1:
267 """Raise the pool's release threshold to ULLONG_MAX if currently zero.
269 By default the release threshold is 0, meaning memory is returned to
270 the OS as soon as there are no active suballocations. Setting it to
271 ULLONG_MAX avoids repeated OS round-trips.
272 """
273 cdef cydriver.cuuint64_t current_threshold
274 cdef cydriver.cuuint64_t max_threshold = ULLONG_MAX 2. / : } ~ abbbcbdbebfbgbhbibjb; = kblbnbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$b%b'b(b)b*b+b,b-b.b/b:b;b=b?b@b[b]b^b_b`b{b|b}b~bacbcccdcecfc
275 with nogil: 2. / : } ~ abbbcbdbebfbgbhbibjb; = kblbnbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$b%b'b(b)b*b+b,b-b.b/b:b;b=b?b@b[b]b^b_b`b{b|b}b~bacbcccdcecfc
276 HANDLE_RETURN( 2. / : } ~ abbbcbdbebfbgbhbibjb; = kblbnbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$b%b'b(b)b*b+b,b-b.b/b:b;b=b?b@b[b]b^b_b`b{b|b}b~bacbcccdcecfc
277 cydriver.cuMemPoolGetAttribute( 2. / : } ~ abbbcbdbebfbgbhbibjb; = kblbnbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$b%b'b(b)b*b+b,b-b.b/b:b;b=b?b@b[b]b^b_b`b{b|b}b~bacbcccdcecfc
278 as_cu(self._h_pool),
279 cydriver.CUmemPool_attribute.CU_MEMPOOL_ATTR_RELEASE_THRESHOLD,
280 ¤t_threshold
281 )
282 )
283 if current_threshold == 0: 2. / : } ~ abbbcbdbebfbgbhbibjb; = kblbnbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$b%b'b(b)b*b+b,b-b.b/b:b;b=b?b@b[b]b^b_b`b{b|b}b~bacbcccdcecfc
284 HANDLE_RETURN(cydriver.cuMemPoolSetAttribute( 1|
285 as_cu(self._h_pool),
286 cydriver.CUmemPool_attribute.CU_MEMPOOL_ATTR_RELEASE_THRESHOLD,
287 &max_threshold
288 ))
289 return 0 2. / : } ~ abbbcbdbebfbgbhbibjb; = kblbnbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$b%b'b(b)b*b+b,b-b.b/b:b;b=b?b@b[b]b^b_b`b{b|b}b~bacbcccdcecfc
292# Raise an exception if the given stream is capturing.
293# A result of CU_STREAM_CAPTURE_STATUS_INVALIDATED is considered an error.
294cdef inline int check_not_capturing(cydriver.CUstream s) except?-1 nogil:
295 cdef cydriver.CUstreamCaptureStatus capturing
296 HANDLE_RETURN(cydriver.cuStreamIsCapturing(s, &capturing)) 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
297 if capturing != cydriver.CUstreamCaptureStatus.CU_STREAM_CAPTURE_STATUS_NONE: 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
298 raise RuntimeError("_MemPool cannot perform memory operations on " 1./:
299 "a capturing stream (consider using GraphMemoryResource).")
302cdef inline Buffer _MP_allocate(_MemPool self, size_t size, Stream stream):
303 cdef cydriver.CUstream s = as_cu(stream._h_stream) 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
304 cdef DevicePtrHandle h_ptr
305 with nogil: 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
306 check_not_capturing(s) 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
307 h_ptr = deviceptr_alloc_from_pool(size, self._h_pool, stream._h_stream) 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
308 if not h_ptr: 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
309 raise RuntimeError("Failed to allocate memory from pool")
310 return Buffer_from_deviceptr_handle(h_ptr, size, self, None) 2. / : } ~ abbbcbdbebfbq r #c$cu v %c'c(c)c*c+c,c-c.c/c:c;c=c?c@c[c]c^c_c`c{c|c}c~cadbdw x cdddedfd9c!cy z A B s t gbhbibjb; = 5 I ? C kbJ ^ j f k g d e l h m i b a c 6 lb_ ` 7 D K nbobpbqbrbsbtbubvbwbxbybzbAbBbCbDb| EbFbGbHbIbJbKbLbMbNbObPbQbRbSbTbUbVbWbXbYbZb0b1b2b3b4b5b6b7b8b9b!b#b$bV W %b'b(b)b*b+b,b-b.bgd/bhd:b;b=bidjd?b@bkdldmd[bnd]bod^b_b`bpdqd{brdsdtdud|bvd}b~bacbcccdcwdxdecfc
313cdef inline void _MP_deallocate(
314 _MemPool self, uintptr_t ptr, size_t size, Stream stream
315) noexcept nogil:
316 cdef cydriver.CUstream s = as_cu(stream._h_stream)
317 cdef cydriver.CUdeviceptr devptr = <cydriver.CUdeviceptr>ptr
318 cdef cydriver.CUresult r
319 with nogil:
320 r = cydriver.cuMemFreeAsync(devptr, s)
321 if r != cydriver.CUDA_ERROR_INVALID_CONTEXT:
322 HANDLE_RETURN(r)
325cdef inline _MP_close(_MemPool self):
326 if not self._h_pool: 2KdLdq Mdr NdOdPdu Qdv RdSdTdUdVdWdXdYdZd0d1d2d3d4d5d6d7d8d9d!d#d$d%d'd(d)d*d+d,d-d.d/d:d;d=d?d@d[d]d^d_dw x `d{d|d}d~daey z A B s t L n M D K mb{ ) * + , -
327 return
329 # Reset members in declaration order.
330 # The RAII deleter calls cuMemPoolDestroy if this is an owning handle.
331 self._h_pool.reset() 2KdLdq Mdr NdOdPdu Qdv RdSdTdUdVdWdXdYdZd0d1d2d3d4d5d6d7d8d9d!d#d$d%d'd(d)d*d+d,d-d.d/d:d;d=d?d@d[d]d^d_dw x `d{d|d}d~daey z A B s t L n M D K mb{ ) * + , -
332 self._mempool_owned = False 2KdLdq Mdr NdOdPdu Qdv RdSdTdUdVdWdXdYdZd0d1d2d3d4d5d6d7d8d9d!d#d$d%d'd(d)d*d+d,d-d.d/d:d;d=d?d@d[d]d^d_dw x `d{d|d}d~daey z A B s t L n M D K mb{ ) * + , -
333 self._ipc_data = None 2KdLdq Mdr NdOdPdu Qdv RdSdTdUdVdWdXdYdZd0d1d2d3d4d5d6d7d8d9d!d#d$d%d'd(d)d*d+d,d-d.d/d:d;d=d?d@d[d]d^d_dw x `d{d|d}d~daey z A B s t L n M D K mb{ ) * + , -
334 self._attributes = None 2KdLdq Mdr NdOdPdu Qdv RdSdTdUdVdWdXdYdZd0d1d2d3d4d5d6d7d8d9d!d#d$d%d'd(d)d*d+d,d-d.d/d:d;d=d?d@d[d]d^d_dw x `d{d|d}d~daey z A B s t L n M D K mb{ ) * + , -