version 1.2, 2012/06/25 19:51:01
|
version 1.4, 2015/04/20 18:19:52
|
|
|
#include <assert.h> | #include <assert.h> |
#include <new> | #include <new> |
#include <common.h> | #include <common.h> |
|
#include <pal/atomic.h> |
#include "types.h" | #include "types.h" |
#include "instance.h" | #include "instance.h" |
| |
|
|
| |
struct header | struct header |
{ | { |
AtomicType m_refCounter; |
volatile ptrdiff_t m_refCounter; |
MI_Uint32 m_capacity; | MI_Uint32 m_capacity; |
}; | }; |
| |
|
|
header* chunk = (header*)operator new(sizeof(header) + capacity * v_traits->size); | header* chunk = (header*)operator new(sizeof(header) + capacity * v_traits->size); |
| |
chunk->m_capacity = capacity; | chunk->m_capacity = capacity; |
AtomicSet(chunk->m_refCounter, 0); |
Atomic_Swap(&chunk->m_refCounter, 0); |
| |
return (chunk + 1); | return (chunk + 1); |
} | } |
|
|
inline static void AddRef(void* data) | inline static void AddRef(void* data) |
{ | { |
if ( data ) | if ( data ) |
AtomicInc(GetHeader(data)->m_refCounter); |
Atomic_Inc(&GetHeader(data)->m_refCounter); |
} | } |
| |
static void Release(void* v_this, const ArrayTraits* v_traits) | static void Release(void* v_this, const ArrayTraits* v_traits) |
{ | { |
Array_data* v = (Array_data*)v_this; | Array_data* v = (Array_data*)v_this; |
if ( v->p && | if ( v->p && |
AtomicDec(GetHeader(v->p)->m_refCounter)) |
Atomic_Dec(&GetHeader(v->p)->m_refCounter) == 0) |
{ | { |
if (v_traits->dtor) | if (v_traits->dtor) |
v_traits->dtor(v->p,v->size); | v_traits->dtor(v->p,v->size); |
|
|
void __ArrayCOW(void* v_this, const ArrayTraits* v_traits) | void __ArrayCOW(void* v_this, const ArrayTraits* v_traits) |
{ | { |
Array_data* v = (Array_data*)v_this; | Array_data* v = (Array_data*)v_this; |
if ( v->p && AtomicGet(GetHeader(v->p)->m_refCounter) != 1 ) |
if ( v->p && Atomic_Read(&GetHeader(v->p)->m_refCounter) != 1 ) |
{ | { |
void* new_data = Allocate(v->size,v_traits); | void* new_data = Allocate(v->size,v_traits); |
| |