44#include <cx/debug/dbgtypes.h>
47#define sarrayref(typ) sa_##typ
48#define sarrayhdl(typ) sa_##typ*
78#define saDeclareType(name, typ) \
79 typedef union sa_##name { \
82 void* _is_sarray_##name; \
91#define saDeclare(name) saDeclareType(name, name)
98#define saDeclarePtr(name) saDeclareType(name, name*)
103#define saInitNone { .a = 0 }
106typedef sa_ref sa_opaque;
133typedef struct SArrayHeader {
150 SAINT_Extended = 0x8000,
154enum SARRAY_GROW_ENUM {
185 SAINT_Consume = 0x10000000,
188#define SA_GROW_MASK (0xff000000)
230#define SA_Grow(rate) (((uint32)SA_GROW_##rate) << 24)
233#define SA_GET_GROW(flags) ((flags) >> 24)
235#define SARRAY_HDRSIZE (offsetof(SArrayHeader, data))
236#define SARRAY_HDR(ref) ((SArrayHeader*)(((uintptr)((ref).a)) - SARRAY_HDRSIZE))
237#define SAREF(r) (unused_noeval(&((r)._is_sarray)), *(sa_ref*)(&(r)))
238#define SAHANDLE(h) ((sahandle)(unused_noeval((h != NULL) && &((h)->_is_sarray)), (h)))
240_Ret_notnull_ _meta_inline SArrayHeader* _saHdr(_In_ sa_ref ref)
242 return SARRAY_HDR(ref);
251#define saSize(ref) ((ref)._is_sarray ? _saHdr(SAREF(ref))->count : 0)
259#define saCapacity(ref) ((ref)._is_sarray ? _saHdr(SAREF(ref))->capacity : 0)
267#define saElemSize(ref) ((ref)._is_sarray ? stGetSize(_saHdr(SAREF(ref))->elemtype) : 0)
275#define saElemType(ref) ((ref)._is_sarray ? _saHdr(SAREF(ref))->elemtype : 0)
283#define saValid(ref) ((ref).a)
292_Success_(!canfail ||
return)
293_When_(canfail, _Check_return_)
294_At_(out->a, _Post_notnull_)
bool _saInit(_Out_ sahandle out, stype elemtype, _In_opt_ STypeOps* ops, int32 capacity,
295 bool canfail, flags_t flags);
318#define saInit(out, type, capacity, ...) \
319 _saInit(SAHANDLE(out), stFullType(type), capacity, false, opt_flags(__VA_ARGS__))
330#define saTryInit(out, type, capacity, ...) \
331 _saInit(SAHANDLE(out), stFullType(type), capacity, true, opt_flags(__VA_ARGS__))
333_At_(handle->a, _Pre_maybenull_ _Post_null_)
void _saDestroy(_Inout_ sahandle handle);
348#define saDestroy(handle) _saDestroy(SAHANDLE(handle))
350_When_(canfail, _Check_return_)
353 _Post_notnull_)
bool _saReserve(_Inout_ sahandle handle, int32 capacity,
bool canfail);
370#define saReserve(handle, capacity) _saReserve(SAHANDLE(handle), capacity, true)
373 _Pre_notnull_ _Post_notnull_)
void _saShrink(_Inout_ sahandle handle, int32 capacity);
392#define saShrink(handle, capacity) _saShrink(SAHANDLE(handle), capacity)
394_At_(handle->a, _Pre_notnull_ _Post_notnull_)
void _saSetSize(_Inout_ sahandle handle, int32 size);
410#define saSetSize(handle, size) _saSetSize(SAHANDLE(handle), size)
412_At_(handle->a, _Pre_maybenull_)
void _saClear(_Inout_ sahandle handle);
427#define saClear(handle) _saClear(SAHANDLE(handle))
436#define _sa_Consume_Arg_ \
437 _When_(flags& SAINT_Consume, _Pre_notnull_ _Post_invalid_) \
438 _When_(!(flags & SAINT_Consume), _Inout_)
439_At_(handle->a, _Pre_maybenull_ _Post_notnull_) int32 _saPush(_Inout_ sahandle handle, stype elemtype, _In_ stgeneric elem,
441_At_(handle->a, _Pre_maybenull_ _Post_notnull_) int32 _saPushPtr(_Inout_ sahandle handle, stype elemtype,
442 _sa_Consume_Arg_ stgeneric* elem, flags_t flags);
467#define saPush(handle, type, elem, ...) \
468 _saPush(SAHANDLE(handle), stCheckedArg(type, elem), opt_flags(__VA_ARGS__))
493#define saPushC(handle, type, elem, ...) \
494 _saPushPtr(SAHANDLE(handle), \
495 stCheckedPtrArg(type, elem), \
496 opt_flags(__VA_ARGS__) | SAINT_Consume)
498_Ret_opt_valid_ _At_(handle->a,
499 _Pre_maybenull_)
void* _saPopPtr(_Inout_ sahandle handle, int32 idx);
518#define saPopPtr(handle) _saPopPtr(SAHANDLE(handle), -1)
535#define saPopPtrI(handle, idx) _saPopPtr(SAHANDLE(handle), idx)
537_At_(ref.a, _Pre_notnull_) int32 _saFind(_In_ sa_ref ref, _In_ stgeneric elem, flags_t flags);
538_At_(ref.a, _Pre_maybenull_) _meta_inline int32
539_saFindChecked(_In_ sa_ref ref, stype elemtype, _In_ stgeneric elem, flags_t flags)
544 return _saFind(ref, elem, flags);
569#define saFind(ref, type, elem, ...) \
570 _saFindChecked(SAREF(ref), stCheckedArg(type, elem), opt_flags(__VA_ARGS__))
575 _Post_notnull_)
bool _saFindRemove(_Inout_ sahandle handle, _In_ stgeneric elem, flags_t flags);
576_At_(handle->a, _Pre_maybenull_) _meta_inline
bool
577_saFindRemoveChecked(_Inout_ sahandle handle, stype elemtype, _In_ stgeneric elem, flags_t flags)
582 return _saFindRemove(handle, elem, flags);
605#define saFindRemove(handle, type, elem, ...) \
606 _saFindRemoveChecked(SAHANDLE(handle), stCheckedArg(type, elem), opt_flags(__VA_ARGS__))
610 _Post_notnull_) int32 _saInsert(_Inout_ sahandle handle, int32 idx, _In_ stgeneric elem);
611_At_(handle->a, _Pre_notnull_ _Post_notnull_) _meta_inline int32
612_saInsertChecked(_Inout_ sahandle handle, int32 idx, stype elemtype, _In_ stgeneric elem)
616 return _saInsert(handle, idx, elem);
641#define saInsert(handle, idx, type, elem) \
642 _saInsertChecked(SAHANDLE(handle), idx, stCheckedArg(type, elem))
644_At_(handle->a, _Pre_notnull_ _Post_notnull_)
bool _saExtract(_Inout_ sahandle handle, int32 idx, _Inout_opt_ stgeneric* elem,
647_At_(handle->a, _Pre_maybenull_) _meta_inline
bool
648_saExtractChecked(_Inout_ sahandle handle, int32 idx, stype elemtype,
649 _stCopyDest_Anno_opt_(elemtype) stgeneric* elem, flags_t flags)
654 return _saExtract(handle, idx, elem, flags);
680#define saExtract(handle, idx, type, elem_copy_out, ...) \
681 _saExtractChecked(SAHANDLE(handle), \
683 stCheckedPtrArg(type, elem_copy_out), \
684 opt_flags(__VA_ARGS__))
703#define saRemove(handle, idx, ...) \
704 _saExtractChecked(SAHANDLE(handle), idx, stType(none), NULL, opt_flags(__VA_ARGS__))
706_At_(handle->a, _Pre_maybenull_)
void _saSort(_Inout_ sahandle handle,
bool keep);
727#define saSort(handle, keep) _saSort(SAHANDLE(handle), keep)
735_At_(out->a, _When_(ref.a, _Post_notnull_) )
void _saSlice(_Out_ sahandle out, _In_ sa_ref ref, int32 start, int32 end);
757#define saSlice(out, src, start, end) _saSlice(SAHANDLE(out), SAREF(src), start, end)
776#define saClone(out, src) _saSlice(SAHANDLE(out), SAREF(src), 0, 0)
779 _Post_maybenull_)
void _saMerge(_Out_ sahandle out,
int n, _In_ sa_ref* refs, flags_t flags);
798#define saMerge(out, ...) \
799 _saMerge(SAHANDLE(out), \
800 sizeof((sa_ref[]) { __VA_ARGS__ }) / sizeof(sa_ref), \
801 (sa_ref[]) { __VA_ARGS__ }, \
821#define saMergeF(out, flags, ...) \
822 _saMerge(SAHANDLE(out), \
823 sizeof((sa_ref[]) { __VA_ARGS__ }) / sizeof(sa_ref), \
824 (sa_ref[]) { __VA_ARGS__ }, \
Runtime assertion macros and failure handling.
#define saDeclareType(name, typ)
SARRAY_CREATE_FLAGS_ENUM
Creation flags for sarray initialization.
SARRAY_FUNC_FLAGS_ENUM
Operation flags for sarray functions.
@ SA_Ref
Array references data without copying/destroying (pointer types only)
@ SA_Sorted
Maintain sorted order with O(log n) search and O(n) insert.
@ SA_AutoShrink
Automatically release memory when array shrinks.
#define stvar(typen, val)
bool stEq(stype sta, stype stb)
128-bit sortable unique identifier
Macros for suppressing compiler warnings.