Merged revisions 192059 via svnmerge from

https://origsvn.digium.com/svn/asterisk/trunk

........
  r192059 | kpfleming | 2009-05-04 18:24:16 +0200 (Mon, 04 May 2009) | 5 lines
  
  Ensure that astobj2 memory allocations are properly accounted for when MALLOC_DEBUG is used
  
  This commit ensures that all astobj2 allocated objects are properly accounted for in MALLOC_DEBUG mode by passing down the file/function/line information from the module/function that actually called the astobj2 allocation function.
........


git-svn-id: https://origsvn.digium.com/svn/asterisk/branches/1.6.1@192154 65c4cc65-6c06-0410-ace0-fbb531ad65f3
This commit is contained in:
Kevin P. Fleming
2009-05-04 19:20:58 +00:00
parent 2075905520
commit ed8fb52309
2 changed files with 56 additions and 11 deletions

View File

@@ -399,8 +399,7 @@ typedef void (*ao2_destructor_fn)(void *);
* rather, we just call ao2_ref(o, -1); * rather, we just call ao2_ref(o, -1);
*/ */
#ifdef REF_DEBUG #if defined(REF_DEBUG) || defined(__AST_DEBUG_MALLOC)
#define ao2_t_alloc(arg1, arg2, arg3) _ao2_alloc_debug((arg1), (arg2), (arg3), __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_t_alloc(arg1, arg2, arg3) _ao2_alloc_debug((arg1), (arg2), (arg3), __FILE__, __LINE__, __PRETTY_FUNCTION__)
#define ao2_alloc(arg1, arg2) _ao2_alloc_debug((arg1), (arg2), "", __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_alloc(arg1, arg2) _ao2_alloc_debug((arg1), (arg2), "", __FILE__, __LINE__, __PRETTY_FUNCTION__)
@@ -411,9 +410,12 @@ typedef void (*ao2_destructor_fn)(void *);
#define ao2_alloc(arg1,arg2) _ao2_alloc((arg1), (arg2)) #define ao2_alloc(arg1,arg2) _ao2_alloc((arg1), (arg2))
#endif #endif
void *_ao2_alloc_debug(const size_t data_size, ao2_destructor_fn destructor_fn, char *tag, char *file, int line, const char *funcname); void *_ao2_alloc_debug(const size_t data_size, ao2_destructor_fn destructor_fn, char *tag, char *file, int line, const char *funcname);
void *_ao2_alloc(const size_t data_size, ao2_destructor_fn destructor_fn); void *_ao2_alloc(const size_t data_size, ao2_destructor_fn destructor_fn);
/*! @} */
/*! \brief /*! \brief
* Reference/unreference an object and return the old refcount. * Reference/unreference an object and return the old refcount.
@@ -437,15 +439,22 @@ void *_ao2_alloc(const size_t data_size, ao2_destructor_fn destructor_fn);
*/ */
#ifdef REF_DEBUG #ifdef REF_DEBUG
#define ao2_t_ref(arg1,arg2,arg3) _ao2_ref_debug((arg1), (arg2), (arg3), __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_t_ref(arg1,arg2,arg3) _ao2_ref_debug((arg1), (arg2), (arg3), __FILE__, __LINE__, __PRETTY_FUNCTION__)
#define ao2_ref(arg1,arg2) _ao2_ref_debug((arg1), (arg2), "", __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_ref(arg1,arg2) _ao2_ref_debug((arg1), (arg2), "", __FILE__, __LINE__, __PRETTY_FUNCTION__)
#else #else
#define ao2_t_ref(arg1,arg2,arg3) _ao2_ref((arg1), (arg2)) #define ao2_t_ref(arg1,arg2,arg3) _ao2_ref((arg1), (arg2))
#define ao2_ref(arg1,arg2) _ao2_ref((arg1), (arg2)) #define ao2_ref(arg1,arg2) _ao2_ref((arg1), (arg2))
#endif #endif
int _ao2_ref_debug(void *o, int delta, char *tag, char *file, int line, const char *funcname); int _ao2_ref_debug(void *o, int delta, char *tag, char *file, int line, const char *funcname);
int _ao2_ref(void *o, int delta); int _ao2_ref(void *o, int delta);
/*! @} */
/*! \brief /*! \brief
* Lock an object. * Lock an object.
* *
@@ -673,13 +682,18 @@ struct ao2_container;
* destructor is set implicitly. * destructor is set implicitly.
*/ */
#ifdef REF_DEBUG #if defined(REF_DEBUG) || defined(__AST_DEBUG_MALLOC)
#define ao2_t_container_alloc(arg1,arg2,arg3,arg4) _ao2_container_alloc_debug((arg1), (arg2), (arg3), (arg4), __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_t_container_alloc(arg1,arg2,arg3,arg4) _ao2_container_alloc_debug((arg1), (arg2), (arg3), (arg4), __FILE__, __LINE__, __PRETTY_FUNCTION__)
#define ao2_container_alloc(arg1,arg2,arg3) _ao2_container_alloc_debug((arg1), (arg2), (arg3), "", __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_container_alloc(arg1,arg2,arg3) _ao2_container_alloc_debug((arg1), (arg2), (arg3), "", __FILE__, __LINE__, __PRETTY_FUNCTION__)
#else #else
#define ao2_t_container_alloc(arg1,arg2,arg3,arg4) _ao2_container_alloc((arg1), (arg2), (arg3)) #define ao2_t_container_alloc(arg1,arg2,arg3,arg4) _ao2_container_alloc((arg1), (arg2), (arg3))
#define ao2_container_alloc(arg1,arg2,arg3) _ao2_container_alloc((arg1), (arg2), (arg3)) #define ao2_container_alloc(arg1,arg2,arg3) _ao2_container_alloc((arg1), (arg2), (arg3))
#endif #endif
struct ao2_container *_ao2_container_alloc(const unsigned int n_buckets, struct ao2_container *_ao2_container_alloc(const unsigned int n_buckets,
ao2_hash_fn *hash_fn, ao2_callback_fn *cmp_fn); ao2_hash_fn *hash_fn, ao2_callback_fn *cmp_fn);
struct ao2_container *_ao2_container_alloc_debug(const unsigned int n_buckets, struct ao2_container *_ao2_container_alloc_debug(const unsigned int n_buckets,
@@ -690,6 +704,7 @@ struct ao2_container *_ao2_container_alloc_debug(const unsigned int n_buckets,
* Returns the number of elements in a container. * Returns the number of elements in a container.
*/ */
int ao2_container_count(struct ao2_container *c); int ao2_container_count(struct ao2_container *c);
/*@} */ /*@} */
/*! \name Object Management /*! \name Object Management
@@ -720,15 +735,19 @@ int ao2_container_count(struct ao2_container *c);
#define ao2_t_link(arg1, arg2, arg3) _ao2_link_debug((arg1), (arg2), (arg3), __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_t_link(arg1, arg2, arg3) _ao2_link_debug((arg1), (arg2), (arg3), __FILE__, __LINE__, __PRETTY_FUNCTION__)
#define ao2_link(arg1, arg2) _ao2_link_debug((arg1), (arg2), "", __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_link(arg1, arg2) _ao2_link_debug((arg1), (arg2), "", __FILE__, __LINE__, __PRETTY_FUNCTION__)
#else #else
#define ao2_t_link(arg1, arg2, arg3) _ao2_link((arg1), (arg2)) #define ao2_t_link(arg1, arg2, arg3) _ao2_link((arg1), (arg2))
#define ao2_link(arg1, arg2) _ao2_link((arg1), (arg2)) #define ao2_link(arg1, arg2) _ao2_link((arg1), (arg2))
#endif #endif
void *_ao2_link_debug(struct ao2_container *c, void *new_obj, char *tag, char *file, int line, const char *funcname); void *_ao2_link_debug(struct ao2_container *c, void *new_obj, char *tag, char *file, int line, const char *funcname);
void *_ao2_link(struct ao2_container *c, void *newobj); void *_ao2_link(struct ao2_container *c, void *newobj);
/*! /*!
* \brief Remove an object from the container * \brief Remove an object from a container
* *
* \param c the container * \param c the container
* \param obj the object to unlink * \param obj the object to unlink
@@ -744,12 +763,17 @@ void *_ao2_link(struct ao2_container *c, void *newobj);
* refcount will be decremented). * refcount will be decremented).
*/ */
#ifdef REF_DEBUG #ifdef REF_DEBUG
#define ao2_t_unlink(arg1, arg2, arg3) _ao2_unlink_debug((arg1), (arg2), (arg3), __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_t_unlink(arg1, arg2, arg3) _ao2_unlink_debug((arg1), (arg2), (arg3), __FILE__, __LINE__, __PRETTY_FUNCTION__)
#define ao2_unlink(arg1, arg2) _ao2_unlink_debug((arg1), (arg2), "", __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_unlink(arg1, arg2) _ao2_unlink_debug((arg1), (arg2), "", __FILE__, __LINE__, __PRETTY_FUNCTION__)
#else #else
#define ao2_t_unlink(arg1, arg2, arg3) _ao2_unlink((arg1), (arg2)) #define ao2_t_unlink(arg1, arg2, arg3) _ao2_unlink((arg1), (arg2))
#define ao2_unlink(arg1, arg2) _ao2_unlink((arg1), (arg2)) #define ao2_unlink(arg1, arg2) _ao2_unlink((arg1), (arg2))
#endif #endif
void *_ao2_unlink_debug(struct ao2_container *c, void *obj, char *tag, char *file, int line, const char *funcname); void *_ao2_unlink_debug(struct ao2_container *c, void *obj, char *tag, char *file, int line, const char *funcname);
void *_ao2_unlink(struct ao2_container *c, void *obj); void *_ao2_unlink(struct ao2_container *c, void *obj);
@@ -759,6 +783,7 @@ struct ao2_list {
struct ao2_list *next; struct ao2_list *next;
void *obj; /* pointer to the user portion of the object */ void *obj; /* pointer to the user portion of the object */
}; };
/*@} */ /*@} */
/*! \brief /*! \brief
@@ -839,12 +864,17 @@ struct ao2_list {
* be used to free the additional reference possibly created by this function. * be used to free the additional reference possibly created by this function.
*/ */
#ifdef REF_DEBUG #ifdef REF_DEBUG
#define ao2_t_callback(arg1,arg2,arg3,arg4,arg5) _ao2_callback_debug((arg1), (arg2), (arg3), (arg4), (arg5), __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_t_callback(arg1,arg2,arg3,arg4,arg5) _ao2_callback_debug((arg1), (arg2), (arg3), (arg4), (arg5), __FILE__, __LINE__, __PRETTY_FUNCTION__)
#define ao2_callback(arg1,arg2,arg3,arg4) _ao2_callback_debug((arg1), (arg2), (arg3), (arg4), "", __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_callback(arg1,arg2,arg3,arg4) _ao2_callback_debug((arg1), (arg2), (arg3), (arg4), "", __FILE__, __LINE__, __PRETTY_FUNCTION__)
#else #else
#define ao2_t_callback(arg1,arg2,arg3,arg4,arg5) _ao2_callback((arg1), (arg2), (arg3), (arg4)) #define ao2_t_callback(arg1,arg2,arg3,arg4,arg5) _ao2_callback((arg1), (arg2), (arg3), (arg4))
#define ao2_callback(arg1,arg2,arg3,arg4) _ao2_callback((arg1), (arg2), (arg3), (arg4)) #define ao2_callback(arg1,arg2,arg3,arg4) _ao2_callback((arg1), (arg2), (arg3), (arg4))
#endif #endif
void *_ao2_callback_debug(struct ao2_container *c, enum search_flags flags, void *_ao2_callback_debug(struct ao2_container *c, enum search_flags flags,
ao2_callback_fn *cb_fn, void *arg, char *tag, ao2_callback_fn *cb_fn, void *arg, char *tag,
char *file, int line, const char *funcname); char *file, int line, const char *funcname);
@@ -856,12 +886,17 @@ void *_ao2_callback(struct ao2_container *c,
* XXX possibly change order of arguments ? * XXX possibly change order of arguments ?
*/ */
#ifdef REF_DEBUG #ifdef REF_DEBUG
#define ao2_t_find(arg1,arg2,arg3,arg4) _ao2_find_debug((arg1), (arg2), (arg3), (arg4), __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_t_find(arg1,arg2,arg3,arg4) _ao2_find_debug((arg1), (arg2), (arg3), (arg4), __FILE__, __LINE__, __PRETTY_FUNCTION__)
#define ao2_find(arg1,arg2,arg3) _ao2_find_debug((arg1), (arg2), (arg3), "", __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_find(arg1,arg2,arg3) _ao2_find_debug((arg1), (arg2), (arg3), "", __FILE__, __LINE__, __PRETTY_FUNCTION__)
#else #else
#define ao2_t_find(arg1,arg2,arg3,arg4) _ao2_find((arg1), (arg2), (arg3)) #define ao2_t_find(arg1,arg2,arg3,arg4) _ao2_find((arg1), (arg2), (arg3))
#define ao2_find(arg1,arg2,arg3) _ao2_find((arg1), (arg2), (arg3)) #define ao2_find(arg1,arg2,arg3) _ao2_find((arg1), (arg2), (arg3))
#endif #endif
void *_ao2_find_debug(struct ao2_container *c, void *arg, enum search_flags flags, char *tag, char *file, int line, const char *funcname); void *_ao2_find_debug(struct ao2_container *c, void *arg, enum search_flags flags, char *tag, char *file, int line, const char *funcname);
void *_ao2_find(struct ao2_container *c, void *arg, enum search_flags flags); void *_ao2_find(struct ao2_container *c, void *arg, enum search_flags flags);
@@ -961,16 +996,23 @@ struct ao2_iterator {
searches for the next pointer */ searches for the next pointer */
struct ao2_iterator ao2_iterator_init(struct ao2_container *c, int flags); struct ao2_iterator ao2_iterator_init(struct ao2_container *c, int flags);
#ifdef REF_DEBUG #ifdef REF_DEBUG
#define ao2_t_iterator_next(arg1, arg2) _ao2_iterator_next_debug((arg1), (arg2), __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_t_iterator_next(arg1, arg2) _ao2_iterator_next_debug((arg1), (arg2), __FILE__, __LINE__, __PRETTY_FUNCTION__)
#define ao2_iterator_next(arg1) _ao2_iterator_next_debug((arg1), "", __FILE__, __LINE__, __PRETTY_FUNCTION__) #define ao2_iterator_next(arg1) _ao2_iterator_next_debug((arg1), "", __FILE__, __LINE__, __PRETTY_FUNCTION__)
#else #else
#define ao2_t_iterator_next(arg1, arg2) _ao2_iterator_next((arg1)) #define ao2_t_iterator_next(arg1, arg2) _ao2_iterator_next((arg1))
#define ao2_iterator_next(arg1) _ao2_iterator_next((arg1)) #define ao2_iterator_next(arg1) _ao2_iterator_next((arg1))
#endif #endif
void *_ao2_iterator_next_debug(struct ao2_iterator *a, char *tag, char *file, int line, const char *funcname); void *_ao2_iterator_next_debug(struct ao2_iterator *a, char *tag, char *file, int line, const char *funcname);
void *_ao2_iterator_next(struct ao2_iterator *a); void *_ao2_iterator_next(struct ao2_iterator *a);
/* extra functions */ /* extra functions */
void ao2_bt(void); /* backtrace */ void ao2_bt(void); /* backtrace */
#endif /* _ASTERISK_ASTOBJ2_H */ #endif /* _ASTERISK_ASTOBJ2_H */

View File

@@ -130,7 +130,6 @@ static inline struct astobj2 *INTERNAL_OBJ(void *user_data)
/* the underlying functions common to debug and non-debug versions */ /* the underlying functions common to debug and non-debug versions */
static int __ao2_ref(void *user_data, const int delta); static int __ao2_ref(void *user_data, const int delta);
static void *__ao2_alloc(size_t data_size, ao2_destructor_fn destructor_fn);
static struct ao2_container *__ao2_container_alloc(struct ao2_container *c, const uint n_buckets, ao2_hash_fn *hash_fn, static struct ao2_container *__ao2_container_alloc(struct ao2_container *c, const uint n_buckets, ao2_hash_fn *hash_fn,
ao2_callback_fn *cmp_fn); ao2_callback_fn *cmp_fn);
static struct bucket_list *__ao2_link(struct ao2_container *c, void *user_data); static struct bucket_list *__ao2_link(struct ao2_container *c, void *user_data);
@@ -298,7 +297,7 @@ static int __ao2_ref(void *user_data, const int delta)
* We always alloc at least the size of a void *, * We always alloc at least the size of a void *,
* for debugging purposes. * for debugging purposes.
*/ */
static void *__ao2_alloc(size_t data_size, ao2_destructor_fn destructor_fn) static void *__ao2_alloc(size_t data_size, ao2_destructor_fn destructor_fn, char *file, int line, const char *funcname)
{ {
/* allocation */ /* allocation */
struct astobj2 *obj; struct astobj2 *obj;
@@ -306,7 +305,11 @@ static void *__ao2_alloc(size_t data_size, ao2_destructor_fn destructor_fn)
if (data_size < sizeof(void *)) if (data_size < sizeof(void *))
data_size = sizeof(void *); data_size = sizeof(void *);
#if defined(__AST_DEBUG_MALLOC)
obj = __ast_calloc(1, sizeof(*obj) + data_size, file, line, funcname);
#else
obj = ast_calloc(1, sizeof(*obj) + data_size); obj = ast_calloc(1, sizeof(*obj) + data_size);
#endif
if (obj == NULL) if (obj == NULL)
return NULL; return NULL;
@@ -333,7 +336,7 @@ void *_ao2_alloc_debug(size_t data_size, ao2_destructor_fn destructor_fn, char *
void *obj; void *obj;
FILE *refo = fopen(REF_FILE,"a"); FILE *refo = fopen(REF_FILE,"a");
obj = __ao2_alloc(data_size, destructor_fn); obj = __ao2_alloc(data_size, destructor_fn, file, line, funcname);
if (obj == NULL) if (obj == NULL)
return NULL; return NULL;
@@ -349,7 +352,7 @@ void *_ao2_alloc_debug(size_t data_size, ao2_destructor_fn destructor_fn, char *
void *_ao2_alloc(size_t data_size, ao2_destructor_fn destructor_fn) void *_ao2_alloc(size_t data_size, ao2_destructor_fn destructor_fn)
{ {
return __ao2_alloc(data_size, destructor_fn); return __ao2_alloc(data_size, destructor_fn, NULL, 0, NULL);
} }