VTK  9.3.0
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
13#ifndef vtkBuffer_h
14#define vtkBuffer_h
15
16#include "vtkObject.h"
17#include "vtkObjectFactory.h" // New() implementation
18
19#include <algorithm> // for std::min and std::copy
20
21VTK_ABI_NAMESPACE_BEGIN
22template <class ScalarTypeT>
23class vtkBuffer : public vtkObject
24{
25public:
27 typedef ScalarTypeT ScalarType;
28
31
35 inline ScalarType* GetBuffer() { return this->Pointer; }
36 inline const ScalarType* GetBuffer() const { return this->Pointer; }
37
43 void SetBuffer(ScalarType* array, vtkIdType size);
44
48 void SetMallocFunction(vtkMallocingFunction mallocFunction = malloc);
49
53 void SetReallocFunction(vtkReallocingFunction reallocFunction = realloc);
54
61 void SetFreeFunction(bool noFreeFunction, vtkFreeingFunction deleteFunction = free);
62
66 inline vtkIdType GetSize() const { return this->Size; }
67
71 bool Allocate(vtkIdType size);
72
77 bool Reallocate(vtkIdType newsize);
78
79protected:
81 : Pointer(nullptr)
82 , Size(0)
83 {
87 }
88
89 ~vtkBuffer() override { this->SetBuffer(nullptr, 0); }
90
91 ScalarType* Pointer;
96
97private:
98 vtkBuffer(const vtkBuffer&) = delete;
99 void operator=(const vtkBuffer&) = delete;
100};
101
102template <class ScalarT>
104{
106}
107
108template <class ScalarT>
110{
111 auto mkhold = vtkMemkindRAII(true);
113}
114
115//------------------------------------------------------------------------------
116template <typename ScalarT>
118{
119 if (this->Pointer != array)
120 {
121 if (this->DeleteFunction)
122 {
123 this->DeleteFunction(this->Pointer);
124 }
125 this->Pointer = array;
126 }
127 this->Size = size;
128}
129//------------------------------------------------------------------------------
130template <typename ScalarT>
132{
133 this->MallocFunction = mallocFunction;
134}
135//------------------------------------------------------------------------------
136template <typename ScalarT>
138{
139 this->ReallocFunction = reallocFunction;
140}
141
142//------------------------------------------------------------------------------
143template <typename ScalarT>
144void vtkBuffer<ScalarT>::SetFreeFunction(bool noFreeFunction, vtkFreeingFunction deleteFunction)
145{
146 if (noFreeFunction)
147 {
148 this->DeleteFunction = nullptr;
149 }
150 else
151 {
152 this->DeleteFunction = deleteFunction;
153 }
154}
155
156//------------------------------------------------------------------------------
157template <typename ScalarT>
159{
160 // release old memory.
161 this->SetBuffer(nullptr, 0);
162 if (size > 0)
163 {
164 ScalarType* newArray;
165 if (this->MallocFunction)
166 {
167 newArray = static_cast<ScalarType*>(this->MallocFunction(size * sizeof(ScalarType)));
168 }
169 else
170 {
171 newArray = static_cast<ScalarType*>(malloc(size * sizeof(ScalarType)));
172 }
173 if (newArray)
174 {
175 this->SetBuffer(newArray, size);
176 if (!this->MallocFunction)
177 {
178 this->DeleteFunction = free;
179 }
180 return true;
181 }
182 return false;
183 }
184 return true; // size == 0
185}
186
187//------------------------------------------------------------------------------
188template <typename ScalarT>
190{
191 if (newsize == 0)
192 {
193 return this->Allocate(0);
194 }
195
196 if (this->Pointer && this->DeleteFunction != free)
197 {
198 ScalarType* newArray;
199 bool forceFreeFunction = false;
200 if (this->MallocFunction)
201 {
202 newArray = static_cast<ScalarType*>(this->MallocFunction(newsize * sizeof(ScalarType)));
203 if (this->MallocFunction == malloc)
204 {
205 // This must be done because the array passed in may have been
206 // allocated outside of the memory management of `vtkBuffer` and
207 // therefore have been registered with a `DeleteFunction` such as
208 // `delete` or `delete[]`. Since the memory is now allocated with
209 // `malloc` here, we must also reset `DeleteFunction` to something
210 // which matches.
211 forceFreeFunction = true;
212 }
213 }
214 else
215 {
216 newArray = static_cast<ScalarType*>(malloc(newsize * sizeof(ScalarType)));
217 }
218 if (!newArray)
219 {
220 return false;
221 }
222 std::copy(this->Pointer, this->Pointer + (std::min)(this->Size, newsize), newArray);
223 // now save the new array and release the old one too.
224 this->SetBuffer(newArray, newsize);
225 if (!this->MallocFunction || forceFreeFunction)
226 {
227 this->DeleteFunction = free;
228 }
229 }
230 else
231 {
232 // Try to reallocate with minimal memory usage and possibly avoid
233 // copying.
234 ScalarType* newArray = nullptr;
235 if (this->ReallocFunction)
236 {
237 newArray = static_cast<ScalarType*>(
238 this->ReallocFunction(this->Pointer, newsize * sizeof(ScalarType)));
239 }
240 else
241 {
242 newArray = static_cast<ScalarType*>(realloc(this->Pointer, newsize * sizeof(ScalarType)));
243 }
244 if (!newArray)
245 {
246 return false;
247 }
248 this->Pointer = newArray;
249 this->Size = newsize;
250 }
251 return true;
252}
253
254VTK_ABI_NAMESPACE_END
255#endif
256// VTK-HeaderTest-Exclude: vtkBuffer.h
internal storage class used by vtkSOADataArrayTemplate, vtkAOSDataArrayTemplate, and others.
Definition vtkBuffer.h:24
bool Reallocate(vtkIdType newsize)
Allocate a new buffer that holds newsize elements.
Definition vtkBuffer.h:189
ScalarType * Pointer
Definition vtkBuffer.h:91
ScalarType * GetBuffer()
Access the buffer as a scalar pointer.
Definition vtkBuffer.h:35
vtkFreeingFunction DeleteFunction
Definition vtkBuffer.h:95
vtkMallocingFunction MallocFunction
Definition vtkBuffer.h:93
const ScalarType * GetBuffer() const
Definition vtkBuffer.h:36
vtkIdType Size
Definition vtkBuffer.h:92
void SetReallocFunction(vtkReallocingFunction reallocFunction=realloc)
Set the realloc function to be used when allocating space inside this object.
Definition vtkBuffer.h:137
ScalarTypeT ScalarType
Definition vtkBuffer.h:27
static vtkBuffer< ScalarTypeT > * ExtendedNew()
Definition vtkBuffer.h:109
void SetMallocFunction(vtkMallocingFunction mallocFunction=malloc)
Set the malloc function to be used when allocating space inside this object.
Definition vtkBuffer.h:131
vtkIdType GetSize() const
Return the number of elements the current buffer can hold.
Definition vtkBuffer.h:66
~vtkBuffer() override
Definition vtkBuffer.h:89
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:144
vtkReallocingFunction ReallocFunction
Definition vtkBuffer.h:94
bool Allocate(vtkIdType size)
Allocate a new buffer that holds size elements.
Definition vtkBuffer.h:158
static vtkBuffer< ScalarTypeT > * New()
Definition vtkBuffer.h:103
void SetBuffer(ScalarType *array, vtkIdType size)
Set the memory buffer that this vtkBuffer object will manage.
Definition vtkBuffer.h:117
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:49
void *(* vtkMallocingFunction)(size_t)
void *(* vtkReallocingFunction)(void *, size_t)
void(* vtkFreeingFunction)(void *)
#define VTK_STANDARD_NEW_BODY(thisClass)
int vtkIdType
Definition vtkType.h:315