Memory management and reference counting¶
Due to the nature of its domain libcbor will need to work with heap memory. The stateless decoder and encoder don’t allocate any memory.
If you have specific requirements, you should consider rolling your own driver for the stateless API.
Using custom allocator¶
libcbor gives you with the ability to provide your own implementations of malloc
, realloc
, and free
. This can be useful if you are using a custom allocator throughout your application, or if you want to implement custom policies (e.g. tighter restrictions on the amount of allocated memory).
In order to use this feature, libcbor has to be compiled with the appropriate flags
. You can verify the configuration using the CBOR_CUSTOM_ALLOC
macro. A simple usage might be as follows:
#ifdef CBOR_CUSTOM_ALLOC
cbor_set_allocs(malloc, realloc, free);
#else
#error "libcbor built with support for custom allocation is required"
#endif
-
void
cbor_set_allocs
(_cbor_malloc_t custom_malloc, _cbor_realloc_t custom_realloc, _cbor_free_t custom_free)¶ Sets the memory management routines to use.
Only available when CBOR_CUSTOM_ALLOC is defined
Warning
This function modifies the global state and should therefore be used accordingly. Changing the memory handlers while allocated items exist will result in a
free
/malloc
mismatch. This function is not thread safe with respect to both itself and all the other libcbor functions that work with the heap.Note
realloc implementation must correctly support NULL reallocation
- Parameters
custom_malloc
-malloc implementation
custom_realloc
-realloc implementation
custom_free
-free implementation
Reference counting¶
As CBOR items may require complex cleanups at the end of their lifetime, there is a reference counting mechanism in place. This also enables very simple GC when integrating libcbor into managed environment. Every item starts its life (by either explicit creation, or as a result of parsing) with reference count set to 1. When the refcount reaches zero, it will be destroyed.
Items containing nested items will be destroyed recursively - refcount of every nested item will be decreased by one.
The destruction is synchronous and renders any pointers to items with refcount zero invalid immediately after calling the cbor_decref()
.
-
cbor_item_t *
cbor_incref
(cbor_item_t *item)¶ Increases the reference count by one.
No dependent items are affected.
- Return
- the input reference
- Parameters
item[incref]
-item the item
-
void
cbor_decref
(cbor_item_t **item)¶ Decreases the reference count by one, deallocating the item if needed.
In case the item is deallocated, the reference count of any dependent items is adjusted accordingly in a recursive manner.
- Parameters
item[take]
-the item. Set to
NULL
if deallocated
-
void
cbor_intermediate_decref
(cbor_item_t *item)¶ Decreases the reference count by one, deallocating the item if needed.
Convenience wrapper for cbor_decref when its set-to-null behavior is not needed
- Parameters
item[take]
-the item
-
size_t
cbor_refcount
(const cbor_item_t *item)¶ Get the reference count.
Warning
This does not account for transitive references.
- Return
- the reference count
- Parameters
item[borrow]
-the item
-
cbor_item_t *
cbor_move
(cbor_item_t *item)¶ Provide CPP-like move construct.
Decreases the reference count by one, but does not deallocate the item even if it reach zero. This is useful for passing intermediate values to functions that increase reference count, Should only be used with functions that
incref
their arguments.Warning
If the item is moved without correctly increasing the reference count afterwards, the memory will be leaked.
- Return
- the item with reference count decreased by one
- Parameters
item[take]
-the item