mirror of
				https://github.com/asterisk/asterisk.git
				synced 2025-10-31 02:37:10 +00:00 
			
		
		
		
	Convert open-coded linked list in indications to the AST_LIST_* macros. This
cleans the code up some and should make it more maintainable as time goes on. Reviewed by Russell, Kevin, Mark M., and Tilghman via ReviewBoard: http://reviewboard.digium.com/r/34/ git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@155284 65c4cc65-6c06-0410-ace0-fbb531ad65f3
This commit is contained in:
		| @@ -40,9 +40,9 @@ | ||||
| 	   first tone description not preceeded by !. Duration is | ||||
| 	   specified in milliseconds */ | ||||
| struct ind_tone_zone_sound { | ||||
| 	struct ind_tone_zone_sound *next;	/*!< next element */ | ||||
| 	const char *name;			/*!< Identifing name */ | ||||
| 	const char *data;			/*!< Actual zone description */ | ||||
| 	AST_LIST_ENTRY(ind_tone_zone_sound) list; | ||||
| }; | ||||
|  | ||||
| struct ind_tone_zone { | ||||
| @@ -52,7 +52,7 @@ struct ind_tone_zone { | ||||
| 	char description[40];				/*!< Description */ | ||||
| 	int  nrringcadence;				/*!< # registered ringcadence elements */ | ||||
| 	int *ringcadence;				/*!< Ring cadence */ | ||||
| 	struct ind_tone_zone_sound *tones;		/*!< The known tones for this zone */ | ||||
| 	AST_LIST_HEAD_NOLOCK(, ind_tone_zone_sound) tones;		/*!< The known tones for this zone */ | ||||
| }; | ||||
|  | ||||
| /*! \brief set the default tone country */ | ||||
| @@ -62,6 +62,8 @@ int ast_set_indication_country(const char *country); | ||||
| struct ind_tone_zone *ast_get_indication_zone(const char *country); | ||||
| /*! \brief locate a tone_zone_sound, given the tone_zone. if tone_zone == NULL, use the default tone_zone */ | ||||
| struct ind_tone_zone_sound *ast_get_indication_tone(const struct ind_tone_zone *zone, const char *indication); | ||||
| /*! \brief deallocate the passed tone zone */ | ||||
| void ast_destroy_indication_zone(struct ind_tone_zone *zone); | ||||
|  | ||||
| /*! \brief add a new country, if country exists, it will be replaced. */ | ||||
| int ast_register_indication_country(struct ind_tone_zone *country); | ||||
|   | ||||
| @@ -432,7 +432,7 @@ struct ind_tone_zone_sound *ast_get_indication_tone(const struct ind_tone_zone * | ||||
| 	} | ||||
|  | ||||
| 	/* Look through list of tones in the zone searching for the right one */ | ||||
| 	for (ts = zone->tones; ts; ts = ts->next) { | ||||
| 	AST_LIST_TRAVERSE(&zone->tones, ts, list) { | ||||
| 		if (!strcasecmp(ts->name, indication)) | ||||
| 			break; | ||||
| 	} | ||||
| @@ -442,15 +442,21 @@ struct ind_tone_zone_sound *ast_get_indication_tone(const struct ind_tone_zone * | ||||
| 	return ts; | ||||
| } | ||||
|  | ||||
| /* helper function to delete a tone_zone in its entirety */ | ||||
| static inline void free_zone(struct ind_tone_zone* zone) | ||||
| static inline void clear_zone_sound(struct ind_tone_zone_sound *ts) | ||||
| { | ||||
| 	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; | ||||
| 	/* Deconstify the 'const char *'s so the compiler doesn't complain. (but it's safe) */ | ||||
| 	ast_free((char *) ts->name); | ||||
| 	ast_free((char *) ts->data); | ||||
| } | ||||
|  | ||||
| /*! \brief deallocate the passed tone zone */ | ||||
| void ast_destroy_indication_zone(struct ind_tone_zone *zone) | ||||
| { | ||||
| 	struct ind_tone_zone_sound *current; | ||||
|  | ||||
| 	while ((current = AST_LIST_REMOVE_HEAD(&zone->tones, list))) { | ||||
| 		clear_zone_sound(current); | ||||
| 		ast_free(current); | ||||
| 	} | ||||
|  | ||||
| 	if (zone->ringcadence) | ||||
| @@ -477,7 +483,7 @@ int ast_register_indication_country(struct ind_tone_zone *zone) | ||||
| 		/* Remove from the linked list */ | ||||
| 		AST_RWLIST_REMOVE_CURRENT(list); | ||||
| 		/* Finally free the zone itself */ | ||||
| 		free_zone(tz); | ||||
| 		ast_destroy_indication_zone(tz); | ||||
| 		break; | ||||
| 	} | ||||
| 	AST_RWLIST_TRAVERSE_SAFE_END; | ||||
| @@ -512,7 +518,7 @@ int ast_unregister_indication_country(const char *country) | ||||
| 		/* Remove from the list */ | ||||
| 		AST_RWLIST_REMOVE_CURRENT(list); | ||||
| 		ast_verb(3, "Unregistered indication country '%s'\n", tz->country); | ||||
| 		free_zone(tz); | ||||
| 		ast_destroy_indication_zone(tz); | ||||
| 		res = 0; | ||||
| 	} | ||||
| 	AST_RWLIST_TRAVERSE_SAFE_END; | ||||
| @@ -525,37 +531,39 @@ int ast_unregister_indication_country(const char *country) | ||||
|  * exists, it will be replaced. */ | ||||
| int ast_register_indication(struct ind_tone_zone *zone, const char *indication, const char *tonelist) | ||||
| { | ||||
| 	struct ind_tone_zone_sound *ts, *ps; | ||||
| 	struct ind_tone_zone_sound *ts; | ||||
| 	int found = 0; | ||||
|  | ||||
| 	/* is it an alias? stop */ | ||||
| 	if (zone->alias[0]) | ||||
| 		return -1; | ||||
|  | ||||
| 	AST_RWLIST_WRLOCK(&tone_zones); | ||||
| 	for (ps=NULL,ts=zone->tones; ts; ps=ts,ts=ts->next) { | ||||
| 		if (!strcasecmp(indication,ts->name)) { | ||||
| 			/* indication already there, replace */ | ||||
| 			ast_free((void*)ts->name); | ||||
| 			ast_free((void*)ts->data); | ||||
|  | ||||
| 	AST_LIST_TRAVERSE(&zone->tones, ts, list) { | ||||
| 		if (!strcasecmp(indication, ts->name)) { | ||||
| 			clear_zone_sound(ts); | ||||
| 			found = 1; | ||||
| 			break; | ||||
| 		} | ||||
| 	} | ||||
| 	if (!ts) { | ||||
| 		/* not there, we have to add */ | ||||
| 		if (!(ts = ast_malloc(sizeof(*ts)))) { | ||||
| 		if (!(ts = ast_calloc(1, sizeof(*ts)))) { | ||||
| 			AST_RWLIST_UNLOCK(&tone_zones); | ||||
| 			return -2; | ||||
| 		} | ||||
| 		ts->next = NULL; | ||||
| 	} | ||||
| 	if (!(ts->name = ast_strdup(indication)) || !(ts->data = ast_strdup(tonelist))) { | ||||
| 		ast_free(ts); | ||||
| 		AST_RWLIST_UNLOCK(&tone_zones); | ||||
| 		return -2; | ||||
| 	} | ||||
| 	if (ps) | ||||
| 		ps->next = ts; | ||||
| 	else | ||||
| 		zone->tones = ts; | ||||
|  | ||||
| 	if (!found) { | ||||
| 		AST_LIST_INSERT_TAIL(&zone->tones, ts, list); | ||||
| 	} | ||||
|  | ||||
| 	AST_RWLIST_UNLOCK(&tone_zones); | ||||
| 	return 0; | ||||
| } | ||||
| @@ -563,7 +571,7 @@ int ast_register_indication(struct ind_tone_zone *zone, const char *indication, | ||||
| /* remove an existing country's indication. Both country and indication must exist */ | ||||
| int ast_unregister_indication(struct ind_tone_zone *zone, const char *indication) | ||||
| { | ||||
| 	struct ind_tone_zone_sound *ts,*ps = NULL, *tmp; | ||||
| 	struct ind_tone_zone_sound *ts; | ||||
| 	int res = -1; | ||||
|  | ||||
| 	/* is it an alias? stop */ | ||||
| @@ -571,27 +579,18 @@ int ast_unregister_indication(struct ind_tone_zone *zone, const char *indication | ||||
| 		return -1; | ||||
|  | ||||
| 	AST_RWLIST_WRLOCK(&tone_zones); | ||||
| 	ts = zone->tones; | ||||
| 	while (ts) { | ||||
| 		if (!strcasecmp(indication,ts->name)) { | ||||
| 			/* indication found */ | ||||
| 			tmp = ts->next; | ||||
| 			if (ps) | ||||
| 				ps->next = tmp; | ||||
| 			else | ||||
| 				zone->tones = tmp; | ||||
| 			ast_free((void*)ts->name); | ||||
| 			ast_free((void*)ts->data); | ||||
|  | ||||
| 	AST_LIST_TRAVERSE_SAFE_BEGIN(&zone->tones, ts, list) { | ||||
| 		if (!strcasecmp(indication, ts->name)) { | ||||
| 			AST_LIST_REMOVE_CURRENT(list); | ||||
| 			clear_zone_sound(ts); | ||||
| 			ast_free(ts); | ||||
| 			ts = tmp; | ||||
| 			res = 0; | ||||
| 		} | ||||
| 		else { | ||||
| 			/* next zone please */ | ||||
| 			ps = ts; | ||||
| 			ts = ts->next; | ||||
| 			break; | ||||
| 		} | ||||
| 	} | ||||
| 	AST_LIST_TRAVERSE_SAFE_END; | ||||
|  | ||||
| 	/* indication not found, goodbye */ | ||||
| 	AST_RWLIST_UNLOCK(&tone_zones); | ||||
| 	return res; | ||||
|   | ||||
| @@ -216,7 +216,7 @@ static char *handle_cli_indication_show(struct ast_cli_entry *e, int cmd, struct | ||||
| 		int i, j; | ||||
| 		for (i = 2; i < a->argc; i++) { | ||||
| 			if (strcasecmp(tz->country, a->argv[i]) == 0 && !tz->alias[0]) { | ||||
| 				struct ind_tone_zone_sound* ts; | ||||
| 				struct ind_tone_zone_sound *ts; | ||||
| 				if (!found_country) { | ||||
| 					found_country = 1; | ||||
| 					ast_cli(a->fd, "Country Indication      PlayList\n"); | ||||
| @@ -230,8 +230,9 @@ static char *handle_cli_indication_show(struct ast_cli_entry *e, int cmd, struct | ||||
| 					j--; | ||||
| 				ast_copy_string(buf + j, "\n", sizeof(buf) - j); | ||||
| 				ast_cli(a->fd, "%s", buf); | ||||
| 				for (ts = tz->tones; ts; ts = ts->next) | ||||
| 				AST_LIST_TRAVERSE(&tz->tones, ts, list) { | ||||
| 					ast_cli(a->fd, "%-7.7s %-15.15s %s\n", tz->country, ts->name, ts->data); | ||||
| 				} | ||||
| 				break; | ||||
| 			} | ||||
| 		} | ||||
| @@ -276,23 +277,6 @@ static int handle_stopplaytones(struct ast_channel *chan, void *data) | ||||
| 	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 */ | ||||
| static int ind_load_module(int reload) | ||||
| { | ||||
| @@ -347,7 +331,7 @@ static int ind_load_module(int reload) | ||||
| 					}					 | ||||
| 					if (!(tmp = ast_realloc(tones->ringcadence, (tones->nrringcadence + 1) * sizeof(int)))) { | ||||
| 						ast_config_destroy(cfg); | ||||
| 						free_zone(tones); | ||||
| 						ast_destroy_indication_zone(tones); | ||||
| 						return -1; | ||||
| 					} | ||||
| 					tones->ringcadence = tmp; | ||||
| @@ -364,50 +348,49 @@ static int ind_load_module(int reload) | ||||
| 					struct ind_tone_zone* azone; | ||||
| 					if (!(azone = ast_calloc(1, sizeof(*azone)))) { | ||||
| 						ast_config_destroy(cfg); | ||||
| 						free_zone(tones); | ||||
| 						ast_destroy_indication_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); | ||||
| 						free_zone(tones); | ||||
| 						ast_destroy_indication_zone(tones); | ||||
| 					} | ||||
| 					/* next item */ | ||||
| 					country = strsep(&c,","); | ||||
| 				} | ||||
| 			} else { | ||||
| 				struct ind_tone_zone_sound *ts; | ||||
|  | ||||
| 				/* add tone to country */ | ||||
| 				struct ind_tone_zone_sound *ps,*ts; | ||||
| 				for (ps=NULL,ts=tones->tones; ts; ps=ts, ts=ts->next) { | ||||
| 					if (strcasecmp(v->name,ts->name)==0) { | ||||
| 				AST_LIST_TRAVERSE(&tones->tones, ts, list) { | ||||
| 					if (!strcasecmp(v->name, ts->name)) { | ||||
| 						/* already there */ | ||||
| 						ast_log(LOG_NOTICE,"Duplicate entry '%s', skipped.\n",v->name); | ||||
| 						ast_log(LOG_NOTICE, "Duplicate entry '%s' skipped.\n", v->name); | ||||
| 						goto out; | ||||
| 					} | ||||
| 				} | ||||
| 				/* not there, add it to the back */				 | ||||
| 				if (!(ts = ast_malloc(sizeof(*ts)))) { | ||||
|  | ||||
| 				/* not there, add it to the back */ | ||||
| 				if (!(ts = ast_calloc(1, sizeof(*ts)))) { | ||||
| 					ast_config_destroy(cfg); | ||||
| 					return -1; | ||||
| 				} | ||||
| 				ts->next = NULL; | ||||
| 				ts->name = ast_strdup(v->name); | ||||
| 				ts->data = ast_strdup(v->value); | ||||
| 				if (ps) | ||||
| 					ps->next = ts; | ||||
| 				else | ||||
| 					tones->tones = ts; | ||||
|  | ||||
| 				AST_LIST_INSERT_TAIL(&tones->tones, ts, list); | ||||
| 			} | ||||
| out:			v = v->next; | ||||
| 		} | ||||
| 		if (tones->description[0] || tones->alias[0] || tones->tones) { | ||||
| 		if (tones->description[0] || tones->alias[0] || !AST_LIST_EMPTY(&tones->tones)) { | ||||
| 			if (ast_register_indication_country(tones)) { | ||||
| 				ast_log(LOG_WARNING, "Unable to register indication at line %d.\n",v->lineno); | ||||
| 				free_zone(tones); | ||||
| 				ast_destroy_indication_zone(tones); | ||||
| 			} | ||||
| 		} else { | ||||
| 			free_zone(tones); | ||||
| 			ast_destroy_indication_zone(tones); | ||||
| 		} | ||||
|  | ||||
| 		cxt = ast_category_browse(cfg, cxt); | ||||
|   | ||||
		Reference in New Issue
	
	Block a user