VTK  9.5.20250807
vtkBuffer.h
Go to the documentation of this file.
1// SPDX-FileCopyrightText: Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
2// SPDX-License-Identifier: BSD-3-Clause
19#ifndef vtkBuffer_h
20#define vtkBuffer_h
21
22#include "vtkObject.h"
23#include "vtkObjectFactory.h" // New() implementation
24
25#include <algorithm> // for std::min and std::copy
26
27VTK_ABI_NAMESPACE_BEGIN
28template <class ScalarTypeT>
29class vtkBuffer : public vtkObject
30{
31public:
33 typedef ScalarTypeT ScalarType;
34
37
41 ScalarType* GetBuffer() { return this->Pointer; }
42 const ScalarType* GetBuffer() const { return this->Pointer; }
43
49 void SetBuffer(ScalarType* array, vtkIdType size);
50
54 void SetMallocFunction(vtkMallocingFunction mallocFunction = malloc);
55
59 void SetReallocFunction(vtkReallocingFunction reallocFunction = realloc);
60
67 void SetFreeFunction(bool noFreeFunction, vtkFreeingFunction deleteFunction = free);
68
72 vtkIdType GetSize() const { return this->Size; }
73
77 bool Allocate(vtkIdType size);
78
83 bool Reallocate(vtkIdType newsize);
84
85protected:
87 : Pointer(nullptr)
88 , Size(0)
89 {
93 }
94
95 ~vtkBuffer() override { this->SetBuffer(nullptr, 0); }
96
97 ScalarType* Pointer;
102
103private:
104 vtkBuffer(const vtkBuffer&) = delete;
105 void operator=(const vtkBuffer&) = delete;
106};
107
108template <class ScalarT>
110{
112}
113
114template <class ScalarT>
116{
117 auto mkhold = vtkMemkindRAII(true);
119}
120
121//------------------------------------------------------------------------------
122template <typename ScalarT>
124{
125 if (this->Pointer != array)
126 {
127 if (this->DeleteFunction)
128 {
129 this->DeleteFunction(this->Pointer);
130 }
131 this->Pointer = array;
132 }
133 this->Size = sz;
134}
135//------------------------------------------------------------------------------
136template <typename ScalarT>
138{
139 this->MallocFunction = mallocFunction;
140}
141//------------------------------------------------------------------------------
142template <typename ScalarT>
144{
145 this->ReallocFunction = reallocFunction;
146}
147
148//------------------------------------------------------------------------------
149template <typename ScalarT>
150void vtkBuffer<ScalarT>::SetFreeFunction(bool noFreeFunction, vtkFreeingFunction deleteFunction)
151{
152 if (noFreeFunction)
153 {
154 this->DeleteFunction = nullptr;
155 }
156 else
157 {
158 this->DeleteFunction = deleteFunction;
159 }
160}
161
162//------------------------------------------------------------------------------
163template <typename ScalarT>
165{
166 // release old memory.
167 this->SetBuffer(nullptr, 0);
168 if (size > 0)
169 {
170 ScalarType* newArray;
171 if (this->MallocFunction)
172 {
173 newArray = static_cast<ScalarType*>(this->MallocFunction(size * sizeof(ScalarType)));
174 }
175 else
176 {
177 newArray = static_cast<ScalarType*>(malloc(size * sizeof(ScalarType)));
178 }
179 if (newArray)
180 {
181 this->SetBuffer(newArray, size);
182 if (!this->MallocFunction)
183 {
184 this->DeleteFunction = free;
185 }
186 return true;
187 }
188 return false;
189 }
190 return true; // size == 0
191}
192
193//------------------------------------------------------------------------------
194template <typename ScalarT>
196{
197 if (newsize == 0)
198 {
199 return this->Allocate(0);
200 }
201
202 if (this->Pointer && this->DeleteFunction != free)
203 {
204 ScalarType* newArray;
205 bool forceFreeFunction = false;
206 if (this->MallocFunction)
207 {
208 newArray = static_cast<ScalarType*>(this->MallocFunction(newsize * sizeof(ScalarType)));
209 if (this->MallocFunction == malloc)
210 {
211 // This must be done because the array passed in may have been
212 // allocated outside of the memory management of `vtkBuffer` and
213 // therefore have been registered with a `DeleteFunction` such as
214 // `delete` or `delete[]`. Since the memory is now allocated with
215 // `malloc` here, we must also reset `DeleteFunction` to something
216 // which matches.
217 forceFreeFunction = true;
218 }
219 }
220 else
221 {
222 newArray = static_cast<ScalarType*>(malloc(newsize * sizeof(ScalarType)));
223 }
224 if (!newArray)
225 {
226 return false;
227 }
228 std::copy(this->Pointer, this->Pointer + (std::min)(this->Size, newsize), newArray);
229 // now save the new array and release the old one too.
230 this->SetBuffer(newArray, newsize);
231 if (!this->MallocFunction || forceFreeFunction)
232 {
233 this->DeleteFunction = free;
234 }
235 }
236 else
237 {
238 // Try to reallocate with minimal memory usage and possibly avoid
239 // copying.
240 ScalarType* newArray = nullptr;
241 if (this->ReallocFunction)
242 {
243 newArray = static_cast<ScalarType*>(
244 this->ReallocFunction(this->Pointer, newsize * sizeof(ScalarType)));
245 }
246 else
247 {
248 newArray = static_cast<ScalarType*>(realloc(this->Pointer, newsize * sizeof(ScalarType)));
249 }
250 if (!newArray)
251 {
252 return false;
253 }
254 this->Pointer = newArray;
255 this->Size = newsize;
256 }
257 return true;
258}
259
260VTK_ABI_NAMESPACE_END
261#endif
262// VTK-HeaderTest-Exclude: vtkBuffer.h
internal storage class used by vtkSOADataArrayTemplate, vtkAOSDataArrayTemplate, and others.
Definition vtkBuffer.h:30
bool Reallocate(vtkIdType newsize)
Allocate a new buffer that holds newsize elements.
Definition vtkBuffer.h:195
ScalarType * Pointer
Definition vtkBuffer.h:97
ScalarType * GetBuffer()
Access the buffer as a scalar pointer.
Definition vtkBuffer.h:41
vtkFreeingFunction DeleteFunction
Definition vtkBuffer.h:101
vtkMallocingFunction MallocFunction
Definition vtkBuffer.h:99
const ScalarType * GetBuffer() const
Definition vtkBuffer.h:42
vtkIdType Size
Definition vtkBuffer.h:98
void SetReallocFunction(vtkReallocingFunction reallocFunction=realloc)
Set the realloc function to be used when allocating space inside this object.
Definition vtkBuffer.h:143
ScalarTypeT ScalarType
Definition vtkBuffer.h:33
static vtkBuffer< ScalarTypeT > * ExtendedNew()
Definition vtkBuffer.h:115
void SetMallocFunction(vtkMallocingFunction mallocFunction=malloc)
Set the malloc function to be used when allocating space inside this object.
Definition vtkBuffer.h:137
vtkIdType GetSize() const
Return the number of elements the current buffer can hold.
Definition vtkBuffer.h:72
~vtkBuffer() override
Definition vtkBuffer.h:95
vtkTemplateTypeMacro(vtkBuffer< ScalarTypeT >, vtkObject)
void SetFreeFunction(bool noFreeFunction, vtkFreeingFunction deleteFunction=free)
Set the free function to be used when releasing this object.
Definition vtkBuffer.h:150
vtkReallocingFunction ReallocFunction
Definition vtkBuffer.h:100
bool Allocate(vtkIdType size)
Allocate a new buffer that holds size elements.
Definition vtkBuffer.h:164
static vtkBuffer< ScalarTypeT > * New()
Definition vtkBuffer.h:109
void SetBuffer(ScalarType *array, vtkIdType size)
Set the memory buffer that this vtkBuffer object will manage.
Definition vtkBuffer.h:123
A class to help modify and restore the global UsingMemkind state, like SetUsingMemkind(newValue),...
static vtkFreeingFunction GetCurrentFreeFunction()
static vtkMallocingFunction GetCurrentMallocFunction()
static vtkReallocingFunction GetCurrentReallocFunction()
abstract base class for most VTK objects
Definition vtkObject.h:162
void *(* vtkMallocingFunction)(size_t)
void *(* vtkReallocingFunction)(void *, size_t)
void(* vtkFreeingFunction)(void *)
#define VTK_STANDARD_NEW_BODY(thisClass)
int vtkIdType
Definition vtkType.h:332