sead
Loading...
Searching...
No Matches
seadBuffer.h
Go to the documentation of this file.
1#ifndef SEAD_BUFFER_H_
2#define SEAD_BUFFER_H_
3
4#include <basis/seadAssert.h>
5#include <basis/seadNew.h>
6#include <heap/seadHeap.h>
7#include <heap/seadHeapMgr.h>
8
9namespace sead {
10
11template <typename T>
12class Buffer
13{
14private:
15 typedef s32 (*CompareCallback)(const T*, const T*);
16
17public:
19 : mSize(0)
20 , mBuffer(nullptr)
21 {
22 }
23
24 Buffer(s32 size, T* bufferptr)
25 {
26 if (size > 0 && bufferptr != nullptr)
27 {
28 mSize = size;
29 mBuffer = bufferptr;
30 }
31 else
32 {
33 SEAD_ASSERT_MSG(false, "illegal param: size[%d] bufferptr[0x%x]", size, bufferptr);
34 size = 0;
35 bufferptr = nullptr;
36 }
37 }
38
39public:
40 class iterator;
41 class constIterator;
42
44 {
45 public:
46 explicit iterator()
47 : mPtr(nullptr) // mIndex(0)
48 , mBuffer(nullptr)
49 {
50 }
51
52 explicit iterator(Buffer* buffer)
53 : mPtr(buffer->mBuffer) // mIndex(0)
54 , mBuffer(buffer->mBuffer)
55 {
56 }
57
58 iterator(Buffer* buffer, s32 index)
59 : mPtr(&buffer->mBuffer[index]) // mIndex(index)
60 , mBuffer(buffer->mBuffer)
61 {
62 }
63
65 {
66 mPtr++; // mIndex++;
67 return *this;
68 }
69
71 {
72 mPtr--; // mIndex--;
73 return *this;
74 }
75
76 friend bool operator==(const iterator& lhs, const iterator& rhs)
77 {
78 return lhs.mPtr == rhs.mPtr; // lhs.mIndex == rhs.mIndex;
79 }
80
81 friend bool operator!=(const iterator& lhs, const iterator& rhs)
82 {
83 return lhs.mPtr != rhs.mPtr; // lhs.mIndex != rhs.mIndex;
84 }
85
86 T& operator*() const { return *mPtr; } // mBuffer[mIndex];
87 T* operator->() const { return mPtr; } // &(mBuffer[mIndex]);
88
89 s32 getIndex() const { return (uintptr(mPtr) - uintptr(mBuffer)) / sizeof(T); } // mIndex;
90
91 private:
92 T* mPtr; // int mIndex;
94
95 friend class constIterator;
96 };
97
99 {
100 public:
101 explicit constIterator()
102 : mPtr(nullptr) // mIndex(0)
103 , mBuffer(nullptr)
104 {
105 }
106
107 explicit constIterator(const Buffer* buffer)
108 : mPtr(buffer->mBuffer) // mIndex(0)
109 , mBuffer(buffer->mBuffer)
110 {
111 }
112
113 constIterator(const Buffer* buffer, s32 index)
114 : mPtr(&buffer->mBuffer[index]) // mIndex(index)
115 , mBuffer(buffer->mBuffer)
116 {
117 }
118
120 : mPtr(it.mPtr) // mIndex(it.mIndex)
121 , mBuffer(it.mBuffer)
122 {
123 }
124
126 {
127 mPtr++; // mIndex++;
128 return *this;
129 }
130
132 {
133 mPtr--; // mIndex--;
134 return *this;
135 }
136
137 friend bool operator==(const constIterator& lhs, const constIterator& rhs)
138 {
139 return lhs.mPtr == rhs.mPtr; // lhs.mIndex == rhs.mIndex;
140 }
141
142 friend bool operator!=(const constIterator& lhs, const constIterator& rhs)
143 {
144 return lhs.mPtr != rhs.mPtr; // lhs.mIndex != rhs.mIndex;
145 }
146
147 const T& operator*() const { return *mPtr; } // mBuffer[mIndex];
148 const T* operator->() const { return mPtr; } // &(mBuffer[mIndex]);
149
150 s32 getIndex() const { return (uintptr(mPtr) - uintptr(mBuffer)) / sizeof(T); } // mIndex;
151
152 private:
153 const T* mPtr; // int mIndex;
154 const T* mBuffer;
155 };
156
157 // TODO
159
160 // TODO
162
163public:
164 iterator begin() { return iterator(this); }
165 constIterator begin() const { return constIterator(this); }
166
167 iterator end() { return iterator(this, mSize); }
168 constIterator end() const { return constIterator(this, mSize); }
169
171 {
172 if (static_cast<u32>(x) <= static_cast<u32>(mSize))
173 {
174 return iterator(this, x);
175 }
176 else
177 {
178 SEAD_ASSERT_MSG(false, "range over [0,%d] : %d", mSize, x);
179 return end();
180 }
181 }
182
184 {
185 if (static_cast<u32>(x) <= static_cast<u32>(mSize))
186 {
187 return constIterator(this, x);
188 }
189 else
190 {
191 SEAD_ASSERT_MSG(false, "range over [0,%d] : %d", mSize, x);
192 return end();
193 }
194 }
195
196 constIterator constBegin() const { return constIterator(this); }
197
198 constIterator constEnd() const { return constIterator(this, mSize); }
199
201 {
202 if (static_cast<u32>(x) <= static_cast<u32>(mSize))
203 {
204 return constIterator(this, x);
205 }
206 else
207 {
208 SEAD_ASSERT_MSG(false, "range over [0,%d] : %d", mSize, x);
209 return constEnd();
210 }
211 }
212
215
218
221
223
225
227
228public:
229 void allocBuffer(s32 size, s32 alignment = 4)
230 {
231 SEAD_ASSERT(mBuffer == nullptr);
232
233 if (size > 0)
234 {
236 T* buffer = static_cast<T*>(heap->alloc(static_cast<size_t>(size) * sizeof(T), alignment));
237
238 for (s32 i = 0; i < size; i++)
239 new (static_cast<void*>(&buffer[i])) T;
240
241 setBuffer(size, buffer);
242 }
243 else
244 {
245 SEAD_ASSERT_MSG(false, "size[%d] must be larger than zero", size);
246 }
247 }
248
249 void allocBuffer(s32 size, Heap* heap, s32 alignment = 4)
250 {
251 SEAD_ASSERT(mBuffer == nullptr);
252
253 if (size > 0)
254 {
255 if (heap == nullptr) heap = HeapMgr::instance()->getCurrentHeap();
256 T* buffer = static_cast<T*>(heap->alloc(size * sizeof(T), alignment));
257
258 for (s32 i = 0; i < size; i++)
259 new (static_cast<void*>(&buffer[i])) T;
260
261 setBuffer(size, buffer);
262 }
263 else
264 {
265 SEAD_ASSERT_MSG(false, "size[%d] must be larger than zero", size);
266 }
267 }
268
269 bool tryAllocBuffer(s32 size, s32 alignment = 4)
270 {
271 SEAD_ASSERT(mBuffer == nullptr);
272
273 if (size > 0)
274 {
276 T* buffer = static_cast<T*>(heap->alloc(size * sizeof(T), alignment));
277
278 for (s32 i = 0; i < size; i++)
279 new (static_cast<void*>(&buffer[i])) T;
280
281 setBuffer(size, buffer);
282 return true;
283 }
284 else
285 {
286 SEAD_ASSERT_MSG(false, "size[%d] must be larger than zero", size);
287 return false;
288 }
289 }
290
291 bool tryAllocBuffer(s32 size, Heap* heap, s32 alignment = 4)
292 {
293 SEAD_ASSERT(mBuffer == nullptr);
294
295 if (size > 0)
296 {
297 if (heap == nullptr) heap = HeapMgr::instance()->getCurrentHeap();
298 T* buffer = static_cast<T*>(heap->alloc(size * sizeof(T), alignment));
299
300 for (s32 i = 0; i < size; i++)
301 new (static_cast<void*>(&buffer[i])) T;
302
303 setBuffer(size, buffer);
304 return true;
305 }
306 else
307 {
308 SEAD_ASSERT_MSG(false, "size[%d] must be larger than zero", size);
309 return false;
310 }
311 }
312
314 {
315 if (isBufferReady())
316 {
317 for (s32 i = 0; i < mSize; i++)
318 (&mBuffer[i])->~T();
319
321 heap->free(mBuffer);
322
323 mBuffer = nullptr;
324 mSize = 0;
325 }
326 }
327
328 void setBuffer(s32 size, T* bufferptr)
329 {
330 if (size > 0)
331 {
332 if (bufferptr != nullptr)
333 {
334 mSize = size;
335 mBuffer = bufferptr;
336 }
337 else
338 {
339 SEAD_ASSERT_MSG(false, "bufferptr is null");
340 }
341 }
342 else
343 {
344 SEAD_ASSERT_MSG(false, "size[%d] must be larger than zero", size);
345 }
346 }
347
348 bool isBufferReady() const { return mBuffer != nullptr; }
349
351 const T& operator()(s32) const;
352
353 T& operator[] (s32 x)
354 {
355 if (static_cast<u32>(x) < static_cast<u32>(mSize))
356 {
357 return mBuffer[x];
358 }
359 else
360 {
361 SEAD_ASSERT_MSG(false, "index exceeded [%d/%d]", x, mSize);
362 return mBuffer[0];
363 }
364 }
365
366 T& operator[] (u32 x)
367 {
368 if (x < static_cast<u32>(mSize))
369 {
370 return mBuffer[x];
371 }
372 else
373 {
374 SEAD_ASSERT_MSG(false, "index exceeded [%u/%d]", x, mSize);
375 return mBuffer[0];
376 }
377 }
378
379 const T& operator[] (s32 x) const
380 {
381 if (static_cast<u32>(x) < static_cast<u32>(mSize))
382 {
383 return mBuffer[x];
384 }
385 else
386 {
387 SEAD_ASSERT_MSG(false, "index exceeded [%d/%d]", x, mSize);
388 return mBuffer[0];
389 }
390 }
391
392 const T& operator[] (u32 x) const
393 {
394 if (x < static_cast<u32>(mSize))
395 {
396 return mBuffer[x];
397 }
398 else
399 {
400 SEAD_ASSERT_MSG(false, "index exceeded [%u/%d]", x, mSize);
401 return mBuffer[0];
402 }
403 }
404
405 T* get(s32 x)
406 {
407 if (static_cast<u32>(x) < static_cast<u32>(mSize))
408 {
409 return &mBuffer[x];
410 }
411 else
412 {
413 SEAD_ASSERT_MSG(false, "index exceeded [%d/%d]", x, mSize);
414 return nullptr;
415 }
416 }
417
418 const T* get(s32 x) const
419 {
420 if (static_cast<u32>(x) < static_cast<u32>(mSize))
421 {
422 return &mBuffer[x];
423 }
424 else
425 {
426 SEAD_ASSERT_MSG(false, "index exceeded [%d/%d]", x, mSize);
427 return nullptr;
428 }
429 }
430
431 T* unsafeGet(s32 x)
432 {
433 SEAD_ASSERT_MSG(static_cast<u32>(x) < static_cast<u32>(mSize), "index exceeded [%d/%d]", x, mSize);
434 return &mBuffer[x];
435 }
436
437 const T* unsafeGet(s32 x) const
438 {
439 SEAD_ASSERT_MSG(static_cast<u32>(x) < static_cast<u32>(mSize), "index exceeded [%d/%d]", x, mSize);
440 return &mBuffer[x];
441 }
442
443 T& front()
444 {
445 return mBuffer[0];
446 }
447
448 const T& front() const
449 {
450 return mBuffer[0];
451 }
452
453 T& back()
454 {
455 return mBuffer[mSize - 1];
456 }
457
458 const T& back() const
459 {
460 return mBuffer[mSize - 1];
461 }
462
463 s32 size() const { return mSize; }
464
465 s32 getSize() const { return mSize; }
466 T* getBufferPtr() { return mBuffer; }
467 const T* getBufferPtr() const { return mBuffer; }
468 u32 getByteSize() const { return mSize * sizeof(T); }
469
470 Buffer<T>& operator=(const Buffer<T>& rhs)
471 {
472 mSize = rhs.mSize;
473 mBuffer = rhs.mBuffer;
474 return *this;
475 }
476
477 bool isRangeValid(s32 x) const
478 {
479 return static_cast<u32>(x) < static_cast<u32>(mSize);
480 }
481
482 void fill(const T& value)
483 {
484 s32 size = mSize;
485 for (s32 i = 0; i < size; i++)
486 mBuffer[i] = value;
487 }
488
491 s32 binarySearch(const T&) const;
492
493protected:
494 static s32 compareT(const T*, const T*);
495 static s32 defaultBinarySearchCompare(const T&, const T&);
496
497public:
498 template <typename Key>
499 s32 binarySearch(const Key&, s32 (*)(const T&, const Key&)) const;
500
501protected:
504};
505#ifdef cafe
506static_assert(sizeof(Buffer<int>) == 8, "sead::Buffer<T> size mismatch");
507#endif // cafe
508
509} // namespace sead
510
511#endif // SEAD_BUFFER_H_
Definition seadBuffer.h:99
constIterator()
Definition seadBuffer.h:101
constIterator & operator--()
Definition seadBuffer.h:131
const T * operator->() const
Definition seadBuffer.h:148
const T * mPtr
Definition seadBuffer.h:153
friend bool operator!=(const constIterator &lhs, const constIterator &rhs)
Definition seadBuffer.h:142
const T & operator*() const
Definition seadBuffer.h:147
const T * mBuffer
Definition seadBuffer.h:154
constIterator(const Buffer *buffer, s32 index)
Definition seadBuffer.h:113
constIterator(iterator it)
Definition seadBuffer.h:119
s32 getIndex() const
Definition seadBuffer.h:150
constIterator(const Buffer *buffer)
Definition seadBuffer.h:107
constIterator & operator++()
Definition seadBuffer.h:125
friend bool operator==(const constIterator &lhs, const constIterator &rhs)
Definition seadBuffer.h:137
Definition seadBuffer.h:44
friend bool operator==(const iterator &lhs, const iterator &rhs)
Definition seadBuffer.h:76
T * mBuffer
Definition seadBuffer.h:93
T * mPtr
Definition seadBuffer.h:92
iterator(Buffer *buffer)
Definition seadBuffer.h:52
T & operator*() const
Definition seadBuffer.h:86
iterator & operator--()
Definition seadBuffer.h:70
T * operator->() const
Definition seadBuffer.h:87
iterator()
Definition seadBuffer.h:46
friend bool operator!=(const iterator &lhs, const iterator &rhs)
Definition seadBuffer.h:81
iterator & operator++()
Definition seadBuffer.h:64
s32 getIndex() const
Definition seadBuffer.h:89
iterator(Buffer *buffer, s32 index)
Definition seadBuffer.h:58
Definition seadBuffer.h:161
Definition seadBuffer.h:158
Definition seadBuffer.h:13
constIterator toIterator(s32 x) const
Definition seadBuffer.h:183
s32 binarySearch(const T &) const
void heapSort(s32, s32)
constIterator constEnd() const
Definition seadBuffer.h:198
reverseIterator reverseEnd()
void fill(const T &value)
Definition seadBuffer.h:482
iterator toIterator(s32 x)
Definition seadBuffer.h:170
const T * unsafeGet(s32 x) const
Definition seadBuffer.h:437
reverseIterator toReverseIterator(s32)
constIterator end() const
Definition seadBuffer.h:168
void setBuffer(s32 size, T *bufferptr)
Definition seadBuffer.h:328
const T * get(s32 x) const
Definition seadBuffer.h:418
bool tryAllocBuffer(s32 size, Heap *heap, s32 alignment=4)
Definition seadBuffer.h:291
reverseConstIterator reverseConstBegin() const
T * get(s32 x)
Definition seadBuffer.h:405
static s32 defaultBinarySearchCompare(const T &, const T &)
s32 getSize() const
Definition seadBuffer.h:465
Buffer(s32 size, T *bufferptr)
Definition seadBuffer.h:24
T & operator[](s32 x)
Definition seadBuffer.h:353
static s32 compareT(const T *, const T *)
reverseConstIterator reverseEnd() const
T * getBufferPtr()
Definition seadBuffer.h:466
const T & back() const
Definition seadBuffer.h:458
u32 getByteSize() const
Definition seadBuffer.h:468
bool isRangeValid(s32 x) const
Definition seadBuffer.h:477
reverseConstIterator reverseBegin() const
constIterator constBegin() const
Definition seadBuffer.h:196
const T & operator()(s32) const
reverseConstIterator toReverseIterator(s32) const
reverseConstIterator toReverseConstIterator(s32) const
iterator end()
Definition seadBuffer.h:167
T & operator()(s32)
bool isBufferReady() const
Definition seadBuffer.h:348
const T * getBufferPtr() const
Definition seadBuffer.h:467
s32(* CompareCallback)(const T *, const T *)
Definition seadBuffer.h:15
void freeBuffer()
Definition seadBuffer.h:313
reverseConstIterator reverseConstEnd() const
Buffer< T > & operator=(const Buffer< T > &rhs)
Definition seadBuffer.h:470
s32 size() const
Definition seadBuffer.h:463
T * mBuffer
Definition seadBuffer.h:503
s32 mSize
Definition seadBuffer.h:502
constIterator begin() const
Definition seadBuffer.h:165
constIterator toConstIterator(s32 x) const
Definition seadBuffer.h:200
const T & front() const
Definition seadBuffer.h:448
T & front()
Definition seadBuffer.h:443
bool tryAllocBuffer(s32 size, s32 alignment=4)
Definition seadBuffer.h:269
Buffer()
Definition seadBuffer.h:18
reverseIterator reverseBegin()
s32 binarySearch(const Key &, s32(*)(const T &, const Key &)) const
iterator begin()
Definition seadBuffer.h:164
const T & operator[](s32 x) const
Definition seadBuffer.h:379
T * unsafeGet(s32 x)
Definition seadBuffer.h:431
void allocBuffer(s32 size, Heap *heap, s32 alignment=4)
Definition seadBuffer.h:249
T & back()
Definition seadBuffer.h:453
void allocBuffer(s32 size, s32 alignment=4)
Definition seadBuffer.h:229
void heapSort(CompareCallback, s32, s32)
Definition seadHeapMgr.h:21
static HeapMgr * instance()
Definition seadHeapMgr.h:61
Heap * findContainHeap(const void *memBlock) const
Definition seadHeapMgr.cpp:30
Heap * getCurrentHeap() const
Definition seadHeapMgr.cpp:52
Definition seadHeap.h:23
virtual void free(void *ptr)=0
Definition seadAssert.h:44
#define SEAD_ASSERT(condition)
Definition seadAssert.h:24
#define SEAD_ASSERT_MSG(condition, format,...)
Definition seadAssert.h:33