Skip to content

Commit 1b8a2d9

Browse files
committed
Merge pull request #100474 from Ivorforce/cowdata-abstract-realloc
Abstract `CowData`'s reallocations into `_realloc` to consolidate duplicate logic.
2 parents a6e89ba + 8483d79 commit 1b8a2d9

File tree

1 file changed

+25
-19
lines changed

1 file changed

+25
-19
lines changed

core/templates/cowdata.h

Lines changed: 25 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -165,6 +165,7 @@ class CowData {
165165
void _ref(const CowData *p_from);
166166
void _ref(const CowData &p_from);
167167
USize _copy_on_write();
168+
Error _realloc(Size p_alloc_size);
168169

169170
public:
170171
void operator=(const CowData<T> &p_from) { _ref(p_from); }
@@ -344,7 +345,7 @@ Error CowData<T>::resize(Size p_size) {
344345
}
345346

346347
// possibly changing size, copy on write
347-
USize rc = _copy_on_write();
348+
_copy_on_write();
348349

349350
USize current_alloc_size = _get_alloc_size(current_size);
350351
USize alloc_size;
@@ -367,15 +368,10 @@ Error CowData<T>::resize(Size p_size) {
367368
_ptr = _data_ptr;
368369

369370
} else {
370-
uint8_t *mem_new = (uint8_t *)Memory::realloc_static(((uint8_t *)_ptr) - DATA_OFFSET, alloc_size + DATA_OFFSET, false);
371-
ERR_FAIL_NULL_V(mem_new, ERR_OUT_OF_MEMORY);
372-
373-
SafeNumeric<USize> *_refc_ptr = _get_refcount_ptr(mem_new);
374-
T *_data_ptr = _get_data_ptr(mem_new);
375-
376-
new (_refc_ptr) SafeNumeric<USize>(rc); //refcount
377-
378-
_ptr = _data_ptr;
371+
const Error error = _realloc(alloc_size);
372+
if (error) {
373+
return error;
374+
}
379375
}
380376
}
381377

@@ -401,15 +397,10 @@ Error CowData<T>::resize(Size p_size) {
401397
}
402398

403399
if (alloc_size != current_alloc_size) {
404-
uint8_t *mem_new = (uint8_t *)Memory::realloc_static(((uint8_t *)_ptr) - DATA_OFFSET, alloc_size + DATA_OFFSET, false);
405-
ERR_FAIL_NULL_V(mem_new, ERR_OUT_OF_MEMORY);
406-
407-
SafeNumeric<USize> *_refc_ptr = _get_refcount_ptr(mem_new);
408-
T *_data_ptr = _get_data_ptr(mem_new);
409-
410-
new (_refc_ptr) SafeNumeric<USize>(rc); //refcount
411-
412-
_ptr = _data_ptr;
400+
const Error error = _realloc(alloc_size);
401+
if (error) {
402+
return error;
403+
}
413404
}
414405

415406
*_get_size() = p_size;
@@ -418,6 +409,21 @@ Error CowData<T>::resize(Size p_size) {
418409
return OK;
419410
}
420411

412+
template <typename T>
413+
Error CowData<T>::_realloc(Size p_alloc_size) {
414+
uint8_t *mem_new = (uint8_t *)Memory::realloc_static(((uint8_t *)_ptr) - DATA_OFFSET, p_alloc_size + DATA_OFFSET, false);
415+
ERR_FAIL_NULL_V(mem_new, ERR_OUT_OF_MEMORY);
416+
417+
SafeNumeric<USize> *_refc_ptr = _get_refcount_ptr(mem_new);
418+
T *_data_ptr = _get_data_ptr(mem_new);
419+
420+
// If we realloc, we're guaranteed to be the only reference.
421+
new (_refc_ptr) SafeNumeric<USize>(1);
422+
_ptr = _data_ptr;
423+
424+
return OK;
425+
}
426+
421427
template <typename T>
422428
typename CowData<T>::Size CowData<T>::find(const T &p_val, Size p_from) const {
423429
Size ret = -1;

0 commit comments

Comments
 (0)