[asterisk-commits] tilghman: trunk r149199 - in /trunk: channels/ include/asterisk/ main/ pbx/ res/

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Tue Oct 14 17:38:06 CDT 2008


Author: tilghman
Date: Tue Oct 14 17:38:06 2008
New Revision: 149199

URL: http://svn.digium.com/view/asterisk?view=rev&rev=149199
Log:
Add additional memory debugging to several core APIs, and fix several memory
leaks found with these changes.
(Closes issue #13505, closes issue #13543)
Reported by: mav3rick, triccyx
 Patches: 
       20081001__bug13505.diff.txt uploaded by Corydon76 (license 14)
 Tested by: mav3rick, triccyx

Modified:
    trunk/channels/chan_sip.c
    trunk/include/asterisk/chanvars.h
    trunk/include/asterisk/config.h
    trunk/include/asterisk/hashtab.h
    trunk/include/asterisk/strings.h
    trunk/main/chanvars.c
    trunk/main/config.c
    trunk/main/hashtab.c
    trunk/pbx/pbx_spool.c
    trunk/res/res_indications.c

Modified: trunk/channels/chan_sip.c
URL: http://svn.digium.com/view/asterisk/trunk/channels/chan_sip.c?view=diff&rev=149199&r1=149198&r2=149199
==============================================================================
--- trunk/channels/chan_sip.c (original)
+++ trunk/channels/chan_sip.c Tue Oct 14 17:38:06 2008
@@ -21820,6 +21820,12 @@
 	}
 	
 	/* Reset certificate handling for TLS sessions */
+	if (reason != CHANNEL_MODULE_LOAD) {
+		ast_free(default_tls_cfg.certfile);
+		ast_free(default_tls_cfg.cipher);
+		ast_free(default_tls_cfg.cafile);
+		ast_free(default_tls_cfg.capath);
+	}
 	default_tls_cfg.certfile = ast_strdup(AST_CERTFILE); /*XXX Not sure if this is useful */
 	default_tls_cfg.cipher = ast_strdup("");
 	default_tls_cfg.cafile = ast_strdup("");

Modified: trunk/include/asterisk/chanvars.h
URL: http://svn.digium.com/view/asterisk/trunk/include/asterisk/chanvars.h?view=diff&rev=149199&r1=149198&r2=149199
==============================================================================
--- trunk/include/asterisk/chanvars.h (original)
+++ trunk/include/asterisk/chanvars.h Tue Oct 14 17:38:06 2008
@@ -33,7 +33,12 @@
 
 AST_LIST_HEAD_NOLOCK(varshead, ast_var_t);
 
+#ifdef MALLOC_DEBUG
+struct ast_var_t *_ast_var_assign(const char *name, const char *value, const char *file, int lineno, const char *function);
+#define ast_var_assign(a,b)	_ast_var_assign(a,b,__FILE__,__LINE__,__PRETTY_FUNCTION__)
+#else
 struct ast_var_t *ast_var_assign(const char *name, const char *value);
+#endif
 void ast_var_delete(struct ast_var_t *var);
 const char *ast_var_name(const struct ast_var_t *var);
 const char *ast_var_full_name(const struct ast_var_t *var);

Modified: trunk/include/asterisk/config.h
URL: http://svn.digium.com/view/asterisk/trunk/include/asterisk/config.h?view=diff&rev=149199&r1=149198&r2=149199
==============================================================================
--- trunk/include/asterisk/config.h (original)
+++ trunk/include/asterisk/config.h Tue Oct 14 17:38:06 2008
@@ -364,7 +364,12 @@
 struct ast_variable *ast_category_detach_variables(struct ast_category *cat);
 void ast_category_rename(struct ast_category *cat, const char *name);
 
+#ifdef MALLOC_DEBUG
+struct ast_variable *_ast_variable_new(const char *name, const char *value, const char *filename, const char *file, const char *function, int lineno);
+#define ast_variable_new(a, b, c) _ast_variable_new(a, b, c, __FILE__, __PRETTY_FUNCTION__, __LINE__)
+#else
 struct ast_variable *ast_variable_new(const char *name, const char *value, const char *filename);
+#endif
 struct ast_config_include *ast_include_new(struct ast_config *conf, const char *from_file, const char *included_file, int is_exec, const char *exec_file, int from_lineno, char *real_included_file_name, int real_included_file_name_size);
 struct ast_config_include *ast_include_find(struct ast_config *conf, const char *included_file);
 void ast_include_rename(struct ast_config *conf, const char *from_file, const char *to_file);

Modified: trunk/include/asterisk/hashtab.h
URL: http://svn.digium.com/view/asterisk/trunk/include/asterisk/hashtab.h?view=diff&rev=149199&r1=149198&r2=149199
==============================================================================
--- trunk/include/asterisk/hashtab.h (original)
+++ trunk/include/asterisk/hashtab.h Tue Oct 14 17:38:06 2008
@@ -189,12 +189,22 @@
  * \param hash a func ptr to do the hashing
  * \param do_locking use locks to guarantee safety of iterators/insertion/deletion -- real simpleminded right now
 */
+#if (defined(MALLOC_DEBUG) && !defined(STANDALONE))
+struct ast_hashtab * _ast_hashtab_create(int initial_buckets,
+					int (*compare)(const void *a, const void *b), 
+					int (*resize)(struct ast_hashtab *),	
+					int (*newsize)(struct ast_hashtab *tab),
+					unsigned int (*hash)(const void *obj), 
+					int do_locking, const char *file, int lineno, const char *function);
+#define ast_hashtab_create(a,b,c,d,e,f)	_ast_hashtab_create(a,b,c,d,e,f,__FILE__,__LINE__,__PRETTY_FUNCTION__)
+#else
 struct ast_hashtab * ast_hashtab_create(int initial_buckets,
 					int (*compare)(const void *a, const void *b), 
 					int (*resize)(struct ast_hashtab *),	
 					int (*newsize)(struct ast_hashtab *tab),
 					unsigned int (*hash)(const void *obj), 
 					int do_locking );
+#endif
 
 /*!
  * \brief This func will free the hash table and all its memory. 

Modified: trunk/include/asterisk/strings.h
URL: http://svn.digium.com/view/asterisk/trunk/include/asterisk/strings.h?view=diff&rev=149199&r1=149198&r2=149199
==============================================================================
--- trunk/include/asterisk/strings.h (original)
+++ trunk/include/asterisk/strings.h Tue Oct 14 17:38:06 2008
@@ -404,6 +404,30 @@
 /*!
  * Make space in a new string (e.g. to read in data from a file)
  */
+#if (defined(MALLOC_DEBUG) && !defined(STANDALONE))
+AST_INLINE_API(
+int _ast_str_make_space(struct ast_str **buf, size_t new_len, const char *file, int lineno, const char *function),
+{
+	_DB1(struct ast_str *old_buf = *buf;)
+
+	if (new_len <= (*buf)->len) 
+		return 0;	/* success */
+	if ((*buf)->ts == DS_ALLOCA || (*buf)->ts == DS_STATIC)
+		return -1;	/* cannot extend */
+	*buf = (struct ast_str *)__ast_realloc(*buf, new_len + sizeof(struct ast_str), file, lineno, function);
+	if (*buf == NULL) /* XXX watch out, we leak memory here */
+		return -1;
+	if ((*buf)->ts != DS_MALLOC) {
+		pthread_setspecific((*buf)->ts->key, *buf);
+		_DB1(__ast_threadstorage_object_replace(old_buf, *buf, new_len + sizeof(struct ast_str));)
+	}
+
+	(*buf)->len = new_len;
+	return 0;
+}
+)
+#define ast_str_make_space(a,b)	_ast_str_make_space(a,b,__FILE__,__LINE__,__PRETTY_FUNCTION__)
+#else
 AST_INLINE_API(
 int ast_str_make_space(struct ast_str **buf, size_t new_len),
 {
@@ -425,6 +449,7 @@
 	return 0;
 }
 )
+#endif
 
 #define ast_str_alloca(init_len)			\
 	({						\

Modified: trunk/main/chanvars.c
URL: http://svn.digium.com/view/asterisk/trunk/main/chanvars.c?view=diff&rev=149199&r1=149198&r2=149199
==============================================================================
--- trunk/main/chanvars.c (original)
+++ trunk/main/chanvars.c Tue Oct 14 17:38:06 2008
@@ -31,13 +31,21 @@
 #include "asterisk/strings.h"
 #include "asterisk/utils.h"
 
+#ifdef MALLOC_DEBUG
+struct ast_var_t *_ast_var_assign(const char *name, const char *value, const char *file, int lineno, const char *function)
+#else
 struct ast_var_t *ast_var_assign(const char *name, const char *value)
+#endif
 {	
 	struct ast_var_t *var;
 	int name_len = strlen(name) + 1;
 	int value_len = strlen(value) + 1;
 
+#ifdef MALLOC_DEBUG
+	if (!(var = __ast_calloc(sizeof(*var) + name_len + value_len, sizeof(char), file, lineno, function))) {
+#else
 	if (!(var = ast_calloc(sizeof(*var) + name_len + value_len, sizeof(char)))) {
+#endif
 		return NULL;
 	}
 

Modified: trunk/main/config.c
URL: http://svn.digium.com/view/asterisk/trunk/main/config.c?view=diff&rev=149199&r1=149198&r2=149199
==============================================================================
--- trunk/main/config.c (original)
+++ trunk/main/config.c Tue Oct 14 17:38:06 2008
@@ -230,14 +230,22 @@
 	struct ast_config_include *next; /*!< ptr to next inclusion in the list */
 };
 
+#ifdef MALLOC_DEBUG
+struct ast_variable *_ast_variable_new(const char *name, const char *value, const char *filename, const char *file, const char *func, int lineno) 
+#else
 struct ast_variable *ast_variable_new(const char *name, const char *value, const char *filename) 
+#endif
 {
 	struct ast_variable *variable;
 	int name_len = strlen(name) + 1;	
 	int val_len = strlen(value) + 1;	
 	int fn_len = strlen(filename) + 1;	
 
+#ifdef MALLOC_DEBUG
+	if ((variable = __ast_calloc(1, name_len + val_len + fn_len + sizeof(*variable), file, lineno, func))) {
+#else
 	if ((variable = ast_calloc(1, name_len + val_len + fn_len + sizeof(*variable)))) {
+#endif
 		char *dst = variable->stuff;	/* writable space starts here */
 		variable->name = strcpy(dst, name);
 		dst += name_len;

Modified: trunk/main/hashtab.c
URL: http://svn.digium.com/view/asterisk/trunk/main/hashtab.c?view=diff&rev=149199&r1=149198&r2=149199
==============================================================================
--- trunk/main/hashtab.c (original)
+++ trunk/main/hashtab.c Tue Oct 14 17:38:06 2008
@@ -209,22 +209,40 @@
 	return x;
 }
 
-struct ast_hashtab *ast_hashtab_create(int initial_buckets, 
+struct ast_hashtab *
+#if (defined(MALLOC_DEBUG) && !defined(STANDALONE))
+_ast_hashtab_create
+#else
+ast_hashtab_create
+#endif
+(int initial_buckets, 
 	int (*compare)(const void *a, const void *b), 
 	int (*resize)(struct ast_hashtab *), 
 	int (*newsize)(struct ast_hashtab *tab),
 	unsigned int (*hash)(const void *obj), 
-	int do_locking)
+	int do_locking
+#if (defined(MALLOC_DEBUG) && !defined(STANDALONE))
+	, const char *file, int lineno, const char *function
+#endif
+)
 {
 	struct ast_hashtab *ht;
-	
+
+#if (defined(MALLOC_DEBUG) && !defined(STANDALONE))
+	if (!(ht = __ast_calloc(1, sizeof(*ht), file, lineno, function)))
+#else
 	if (!(ht = ast_calloc(1, sizeof(*ht))))
+#endif
 		return NULL;
 
 	while (!ast_is_prime(initial_buckets)) /* make sure this is prime */
 		initial_buckets++;
 
+#if (defined(MALLOC_DEBUG) && !defined(STANDALONE))
+	if (!(ht->array = __ast_calloc(initial_buckets, sizeof(*(ht->array)), file, lineno, function))) {
+#else
 	if (!(ht->array = ast_calloc(initial_buckets, sizeof(*(ht->array))))) {
+#endif
 		free(ht);
 		return NULL;
 	}

Modified: trunk/pbx/pbx_spool.c
URL: http://svn.digium.com/view/asterisk/trunk/pbx/pbx_spool.c?view=diff&rev=149199&r1=149198&r2=149199
==============================================================================
--- trunk/pbx/pbx_spool.c (original)
+++ trunk/pbx/pbx_spool.c Tue Oct 14 17:38:06 2008
@@ -101,6 +101,9 @@
 
 static void free_outgoing(struct outgoing *o)
 {
+	if (o->vars) {
+		ast_variables_destroy(o->vars);
+	}
 	ast_free(o);
 }
 
@@ -324,9 +327,11 @@
 	if (!ast_strlen_zero(o->app)) {
 		ast_verb(3, "Attempting call on %s/%s for application %s(%s) (Retry %d)\n", o->tech, o->dest, o->app, o->data, o->retries);
 		res = ast_pbx_outgoing_app(o->tech, o->format, o->dest, o->waittime * 1000, o->app, o->data, &reason, 2 /* wait to finish */, o->cid_num, o->cid_name, o->vars, o->account, NULL);
+		o->vars = NULL;
 	} else {
 		ast_verb(3, "Attempting call on %s/%s for %s@%s:%d (Retry %d)\n", o->tech, o->dest, o->exten, o->context,o->priority, o->retries);
 		res = ast_pbx_outgoing_exten(o->tech, o->format, o->dest, o->waittime * 1000, o->context, o->exten, o->priority, &reason, 2 /* wait to finish */, o->cid_num, o->cid_name, o->vars, o->account, NULL);
+		o->vars = NULL;
 	}
 	if (res) {
 		ast_log(LOG_NOTICE, "Call failed to go through, reason (%d) %s\n", reason, ast_channel_reason2str(reason));

Modified: trunk/res/res_indications.c
URL: http://svn.digium.com/view/asterisk/trunk/res/res_indications.c?view=diff&rev=149199&r1=149198&r2=149199
==============================================================================
--- trunk/res/res_indications.c (original)
+++ trunk/res/res_indications.c Tue Oct 14 17:38:06 2008
@@ -247,6 +247,23 @@
 {
 	ast_playtones_stop(chan);
 	return 0;
+}
+
+/* helper function to delete a tone_zone in its entirety */
+static inline void free_zone(struct ind_tone_zone* zone)
+{
+	while (zone->tones) {
+		struct ind_tone_zone_sound *tmp = zone->tones->next;
+		ast_free((void *)zone->tones->name);
+		ast_free((void *)zone->tones->data);
+		ast_free(zone->tones);
+		zone->tones = tmp;
+	}
+
+	if (zone->ringcadence)
+		ast_free(zone->ringcadence);
+
+	ast_free(zone);
 }
 
 /*! \brief load indications module */
@@ -303,6 +320,7 @@
 					}					
 					if (!(tmp = ast_realloc(tones->ringcadence, (tones->nrringcadence + 1) * sizeof(int)))) {
 						ast_config_destroy(cfg);
+						free_zone(tones);
 						return -1;
 					}
 					tones->ringcadence = tmp;
@@ -319,13 +337,14 @@
 					struct ind_tone_zone* azone;
 					if (!(azone = ast_calloc(1, sizeof(*azone)))) {
 						ast_config_destroy(cfg);
+						free_zone(tones);
 						return -1;
 					}
 					ast_copy_string(azone->country, country, sizeof(azone->country));
 					ast_copy_string(azone->alias, cxt, sizeof(azone->alias));
 					if (ast_register_indication_country(azone)) {
 						ast_log(LOG_WARNING, "Unable to register indication alias at line %d.\n",v->lineno);
-						ast_free(tones);
+						free_zone(tones);
 					}
 					/* next item */
 					country = strsep(&c,",");
@@ -358,17 +377,20 @@
 		if (tones->description[0] || tones->alias[0] || tones->tones) {
 			if (ast_register_indication_country(tones)) {
 				ast_log(LOG_WARNING, "Unable to register indication at line %d.\n",v->lineno);
-				ast_free(tones);
+				free_zone(tones);
 			}
-		} else ast_free(tones);
+		} else {
+			free_zone(tones);
+		}
 
 		cxt = ast_category_browse(cfg, cxt);
 	}
 
 	/* determine which country is the default */
 	country = ast_variable_retrieve(cfg,"general","country");
-	if (!country || !*country || ast_set_indication_country(country))
+	if (ast_strlen_zero(country) || ast_set_indication_country(country)) {
 		ast_log(LOG_WARNING,"Unable to set the default country (for indication tones)\n");
+	}
 
 	ast_config_destroy(cfg);
 	return 0;




More information about the asterisk-commits mailing list