summaryrefslogtreecommitdiff
path: root/include
diff options
context:
space:
mode:
authorRichard Mudgett <rmudgett@digium.com>2012-05-16 16:34:42 +0000
committerRichard Mudgett <rmudgett@digium.com>2012-05-16 16:34:42 +0000
commitd4fa095a647a0a8d472f0fd66c8728cb920a0138 (patch)
treee0cb5db500a2e5081b8eb680cc7e019b1da88fba /include
parent5629d662574c7540047aaba0f87c13d4890509cf (diff)
Change ao2 global array to ao2 global object holder.
Review: https://reviewboard.asterisk.org/r/1921/ git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@366663 65c4cc65-6c06-0410-ace0-fbb531ad65f3
Diffstat (limited to 'include')
-rw-r--r--include/asterisk/astobj2.h137
1 files changed, 70 insertions, 67 deletions
diff --git a/include/asterisk/astobj2.h b/include/asterisk/astobj2.h
index c0e17e10c..9a3234ee9 100644
--- a/include/asterisk/astobj2.h
+++ b/include/asterisk/astobj2.h
@@ -565,130 +565,133 @@ int __ao2_trylock(void *a, enum ao2_lock_req lock_how, const char *file, const c
void *ao2_object_get_lockaddr(void *obj);
-/*! Global ao2 array container base structure. */
+/*! Global ao2 object holder structure. */
struct ao2_global_obj {
- /*! Access lock to the global ao2 array container. */
+ /*! Access lock to the held ao2 object. */
ast_rwlock_t lock;
- /*! Number of elements in the global ao2 array container. */
- unsigned int num_elements;
- /*! Global ao2 array container array. */
- void *obj[0];
+ /*! Global ao2 object. */
+ void *obj;
};
/*!
- * \brief Define a structure to be used to hold a global array of ao2 objects, statically initialized.
+ * \brief Define a global object holder to be used to hold an ao2 object, statically initialized.
* \since 11.0
*
- * \param name This will be the name of the defined structure.
- * \param num_objects Number of ao2 objects to contain.
+ * \param name This will be the name of the object holder.
*
* \details
- * This macro creates a structure definition that can be used to
- * hold an array of ao2 objects accessible using an API. The
- * structure is allocated and initialized to be empty.
+ * This macro creates a global object holder that can be used to
+ * hold an ao2 object accessible using an API. The structure is
+ * allocated and initialized to be empty.
*
* Example usage:
* \code
- * static AO2_GLOBAL_OBJ_STATIC(global_cfg, 10);
+ * static AO2_GLOBAL_OBJ_STATIC(global_cfg);
* \endcode
*
- * This would define \c struct \c global_cfg, intended to hold
- * an array of ao2 objects accessible using an API.
+ * This defines global_cfg, intended to hold an ao2 object
+ * accessible using an API.
*/
#ifndef HAVE_PTHREAD_RWLOCK_INITIALIZER
-#define AO2_GLOBAL_OBJ_STATIC(name, num_objects) \
- struct name { \
- struct ao2_global_obj global; \
- void *objs[num_objects]; \
- } name; \
+#define AO2_GLOBAL_OBJ_STATIC(name) \
+ struct ao2_global_obj name; \
static void __attribute__((constructor)) __init_##name(void) \
{ \
- unsigned int idx = (num_objects); \
- ast_rwlock_init(&name.global.lock); \
- name.global.num_elements = idx; \
- while (idx--) { \
- name.global.obj[idx] = NULL; \
- } \
+ ast_rwlock_init(&name.lock); \
+ name.obj = NULL; \
} \
static void __attribute__((destructor)) __fini_##name(void) \
{ \
- unsigned int idx = (num_objects); \
- while (idx--) { \
- if (name.global.obj[idx]) { \
- ao2_ref(name.global.obj[idx], -1); \
- name.global.obj[idx] = NULL; \
- } \
+ if (name.obj) { \
+ ao2_ref(name.obj, -1); \
+ name.obj = NULL; \
} \
- ast_rwlock_destroy(&name.global.lock); \
+ ast_rwlock_destroy(&name.lock); \
} \
struct __dummy_##name
#else
-#define AO2_GLOBAL_OBJ_STATIC(name, num_objects) \
- struct name { \
- struct ao2_global_obj global; \
- void *objs[num_objects]; \
- } name = { \
- .global.lock = AST_RWLOCK_INIT_VALUE, \
- .global.num_elements = (num_objects), \
+#define AO2_GLOBAL_OBJ_STATIC(name) \
+ struct ao2_global_obj name = { \
+ .lock = AST_RWLOCK_INIT_VALUE, \
}
#endif
/*!
- * \brief Release all global ao2 objects in the global array.
+ * \brief Release the ao2 object held in the global holder.
* \since 11.0
*
- * \param array Global ao2 object array container.
+ * \param holder Global ao2 object holder.
* \param tag used for debugging
*
* \return Nothing
*/
-#define ao2_t_global_obj_release(array, tag) \
- __ao2_global_obj_release(&array.global, (tag), __FILE__, __LINE__, __PRETTY_FUNCTION__, #array)
-#define ao2_global_obj_release(array) \
- __ao2_global_obj_release(&array.global, "", __FILE__, __LINE__, __PRETTY_FUNCTION__, #array)
+#define ao2_t_global_obj_release(holder, tag) \
+ __ao2_global_obj_release(&holder, (tag), __FILE__, __LINE__, __PRETTY_FUNCTION__, #holder)
+#define ao2_global_obj_release(holder) \
+ __ao2_global_obj_release(&holder, "", __FILE__, __LINE__, __PRETTY_FUNCTION__, #holder)
-void __ao2_global_obj_release(struct ao2_global_obj *array, const char *tag, const char *file, int line, const char *func, const char *name);
+void __ao2_global_obj_release(struct ao2_global_obj *holder, const char *tag, const char *file, int line, const char *func, const char *name);
/*!
- * \brief Replace a global ao2 object in the global array.
+ * \brief Replace an ao2 object in the global holder.
* \since 11.0
*
- * \param array Global ao2 object array container.
- * \param idx Index to replace in the array.
- * \param obj Object to put into the array. Can be NULL.
+ * \param holder Global ao2 object holder.
+ * \param obj Object to put into the holder. Can be NULL.
* \param tag used for debugging
*
* \note This function automatically increases the reference
- * count to account for the reference that the global array now
+ * count to account for the reference that the global holder now
* holds to the object.
*
- * \retval Reference to previous global ao2 object stored at the index.
+ * \retval Reference to previous global ao2 object stored.
* \retval NULL if no object available.
*/
-#define ao2_t_global_obj_replace(array, idx, obj, tag) \
- __ao2_global_obj_replace(&array.global, (idx), (obj), (tag), __FILE__, __LINE__, __PRETTY_FUNCTION__, #array)
-#define ao2_global_obj_replace(array, idx, obj) \
- __ao2_global_obj_replace(&array.global, (idx), (obj), "", __FILE__, __LINE__, __PRETTY_FUNCTION__, #array)
+#define ao2_t_global_obj_replace(holder, obj, tag) \
+ __ao2_global_obj_replace(&holder, (obj), (tag), __FILE__, __LINE__, __PRETTY_FUNCTION__, #holder)
+#define ao2_global_obj_replace(holder, idx, obj) \
+ __ao2_global_obj_replace(&holder, (obj), "", __FILE__, __LINE__, __PRETTY_FUNCTION__, #holder)
+
+void *__ao2_global_obj_replace(struct ao2_global_obj *holder, void *obj, const char *tag, const char *file, int line, const char *func, const char *name);
-void *__ao2_global_obj_replace(struct ao2_global_obj *array, unsigned int idx, void *obj, const char *tag, const char *file, int line, const char *func, const char *name);
+/*!
+ * \brief Replace an ao2 object in the global holder, throwing away any old object.
+ * \since 11.0
+ *
+ * \param holder Global ao2 object holder.
+ * \param obj Object to put into the holder. Can be NULL.
+ * \param tag used for debugging
+ *
+ * \note This function automatically increases the reference
+ * count to account for the reference that the global holder now
+ * holds to the object. It also decreases the reference count
+ * of any object being replaced.
+ *
+ * \retval 0 The global object was previously empty
+ * \retval 1 The global object was not previously empty
+ */
+#define ao2_t_global_obj_replace_unref(holder, obj, tag) \
+ __ao2_global_obj_replace_unref(&holder, (obj), (tag), __FILE__, __LINE__, __PRETTY_FUNCTION__, #holder)
+#define ao2_global_obj_replace_unref(holder, obj) \
+ __ao2_global_obj_replace_unref(&holder, (obj), "", __FILE__, __LINE__, __PRETTY_FUNCTION__, #holder)
+int __ao2_global_obj_replace_unref(struct ao2_global_obj *holder, void *obj, const char *tag, const char *file, int line, const char *func, const char *name);
/*!
- * \brief Get a reference to the object stored in the ao2 global array.
+ * \brief Get a reference to the object stored in the global holder.
* \since 11.0
*
- * \param array Global ao2 object array container.
- * \param idx Index to get an object reference in the array.
+ * \param holder Global ao2 object holder.
* \param tag used for debugging
*
- * \retval Reference to current global ao2 object stored at the index.
+ * \retval Reference to current ao2 object stored in the holder.
* \retval NULL if no object available.
*/
-#define ao2_t_global_obj_ref(array, idx, tag) \
- __ao2_global_obj_ref(&array.global, (idx), (tag), __FILE__, __LINE__, __PRETTY_FUNCTION__, #array)
-#define ao2_global_obj_ref(array, idx) \
- __ao2_global_obj_ref(&array.global, (idx), "", __FILE__, __LINE__, __PRETTY_FUNCTION__, #array)
+#define ao2_t_global_obj_ref(holder, tag) \
+ __ao2_global_obj_ref(&holder, (tag), __FILE__, __LINE__, __PRETTY_FUNCTION__, #holder)
+#define ao2_global_obj_ref(holder, idx) \
+ __ao2_global_obj_ref(&holder, "", __FILE__, __LINE__, __PRETTY_FUNCTION__, #holder)
-void *__ao2_global_obj_ref(struct ao2_global_obj *array, unsigned int idx, const char *tag, const char *file, int line, const char *func, const char *name);
+void *__ao2_global_obj_ref(struct ao2_global_obj *holder, const char *tag, const char *file, int line, const char *func, const char *name);
/*!