diff options
author | russell <russell@f38db490-d61c-443f-a65b-d21fe96a405b> | 2006-12-09 15:45:37 +0000 |
---|---|---|
committer | russell <russell@f38db490-d61c-443f-a65b-d21fe96a405b> | 2006-12-09 15:45:37 +0000 |
commit | e0c17686858a76e0dc0b62a00e880e183e6f1625 (patch) | |
tree | d034acd6ff92286bd3c3cb7e9e47bd1b6e87a406 /channels/chan_iax2.c | |
parent | 6507d380929432b19b1783e5d14a33e0ebf05b32 (diff) |
Use locking when accessing the registrations list. This list is not actually
used very often, so the likelihood of there being a problem is pretty small,
but still possible. For example, if the CLI command to list the registrations
was called at the same time that a reload was occurring and the registrations
list was getting destroyed and rebuilt, a crash could occur.
git-svn-id: http://svn.digium.com/svn/asterisk/branches/1.2@48361 f38db490-d61c-443f-a65b-d21fe96a405b
Diffstat (limited to 'channels/chan_iax2.c')
-rw-r--r-- | channels/chan_iax2.c | 13 |
1 files changed, 11 insertions, 2 deletions
diff --git a/channels/chan_iax2.c b/channels/chan_iax2.c index 21fcf2604..e896abeb3 100644 --- a/channels/chan_iax2.c +++ b/channels/chan_iax2.c @@ -410,6 +410,7 @@ struct iax2_registry { }; static struct iax2_registry *registrations; +AST_MUTEX_DEFINE_STATIC(reg_lock); /* Don't retry more frequently than every 10 ms, or less frequently than every 5 seconds */ #define MIN_RETRY_TIME 100 @@ -4399,8 +4400,8 @@ static int iax2_show_registry(int fd, int argc, char *argv[]) char iabuf[INET_ADDRSTRLEN]; if (argc != 3) return RESULT_SHOWUSAGE; - ast_mutex_lock(&peerl.lock); ast_cli(fd, FORMAT2, "Host", "Username", "Perceived", "Refresh", "State"); + ast_mutex_lock(®_lock); for (reg = registrations;reg;reg = reg->next) { snprintf(host, sizeof(host), "%s:%d", ast_inet_ntoa(iabuf, sizeof(iabuf), reg->addr.sin_addr), ntohs(reg->addr.sin_port)); if (reg->us.sin_addr.s_addr) @@ -4410,7 +4411,7 @@ static int iax2_show_registry(int fd, int argc, char *argv[]) ast_cli(fd, FORMAT, host, reg->username, perceived, reg->refresh, regstate2str(reg->regstate)); } - ast_mutex_unlock(&peerl.lock); + ast_mutex_unlock(®_lock); return RESULT_SUCCESS; #undef FORMAT #undef FORMAT2 @@ -5624,9 +5625,11 @@ static int iax2_register(char *value, int lineno) reg->addr.sin_family = AF_INET; memcpy(®->addr.sin_addr, hp->h_addr, sizeof(®->addr.sin_addr)); reg->addr.sin_port = porta ? htons(atoi(porta)) : htons(IAX_DEFAULT_PORTNO); + ast_mutex_lock(®_lock); reg->next = registrations; reg->callno = 0; registrations = reg; + ast_mutex_unlock(®_lock); } else { ast_log(LOG_ERROR, "Out of memory\n"); return -1; @@ -8582,6 +8585,7 @@ static void delete_users(void) user = user->next; } ast_mutex_unlock(&userl.lock); + ast_mutex_lock(®_lock); for (reg = registrations;reg;) { regl = reg; reg = reg->next; @@ -8600,6 +8604,7 @@ static void delete_users(void) free(regl); } registrations = NULL; + ast_mutex_unlock(®_lock); ast_mutex_lock(&peerl.lock); for (peer=peerl.peers;peer;) { /* Assume all will be deleted, and we'll find out for sure later */ @@ -8976,8 +8981,10 @@ static int reload_config(void) set_config(config,1); prune_peers(); prune_users(); + ast_mutex_lock(®_lock); for (reg = registrations; reg; reg = reg->next) iax2_do_register(reg); + ast_mutex_unlock(®_lock); /* Qualify hosts, too */ ast_mutex_lock(&peerl.lock); for (peer = peerl.peers; peer; peer = peer->next) @@ -9742,8 +9749,10 @@ int load_module(void) ast_netsock_release(netsock); } + ast_mutex_lock(®_lock); for (reg = registrations; reg; reg = reg->next) iax2_do_register(reg); + ast_mutex_unlock(®_lock); ast_mutex_lock(&peerl.lock); for (peer = peerl.peers; peer; peer = peer->next) { if (peer->sockfd < 0) |