aboutsummaryrefslogtreecommitdiffstats
path: root/channels/chan_iax2.c
diff options
context:
space:
mode:
authordvossel <dvossel@f38db490-d61c-443f-a65b-d21fe96a405b>2009-02-26 16:07:08 +0000
committerdvossel <dvossel@f38db490-d61c-443f-a65b-d21fe96a405b>2009-02-26 16:07:08 +0000
commit447c900c5b6479086cf79bbc12453ea22a213383 (patch)
treeabe2e60313f39e0646219978ecc4ff0ddb6c305c /channels/chan_iax2.c
parent293de5401263141709860c43676079ddb95cfa17 (diff)
Merged revisions 178767 via svnmerge from
https://origsvn.digium.com/svn/asterisk/trunk ........ r178767 | dvossel | 2009-02-26 09:50:22 -0600 (Thu, 26 Feb 2009) | 8 lines IAX2 prune realtime fix Iax2 prune realtime had issues. If "iax2 prune realtime all" was called, it would appear like the command was successful, but in reality nothing happened. This is because the reload that was supposed to take place checks the config files, sees no changes, and does nothing. If there had been a change in the the config file, the realtime users would have been marked for deletion and everything would have been fine. Now prune_users() and prune_peers() are called instead of reload_config() to prune all users/peers that are realtime. These functions remove all users/peers with the rtfriend and delme flags set. iax2_prune_realtime() also lacked the code to properly delete a single friend. For example. if iax2 prune realtime <friend> was called, only the peer instance would be removed. The user would still remain. (closes issue #14479) Reported by: mousepad99 Review: http://reviewboard.digium.com/r/176/ ........ git-svn-id: http://svn.digium.com/svn/asterisk/branches/1.6.1@178769 f38db490-d61c-443f-a65b-d21fe96a405b
Diffstat (limited to 'channels/chan_iax2.c')
-rw-r--r--channels/chan_iax2.c59
1 files changed, 43 insertions, 16 deletions
diff --git a/channels/chan_iax2.c b/channels/chan_iax2.c
index 9a65680c8..4d83dd9e4 100644
--- a/channels/chan_iax2.c
+++ b/channels/chan_iax2.c
@@ -971,8 +971,9 @@ static struct ast_frame *iax2_read(struct ast_channel *c);
static struct iax2_peer *build_peer(const char *name, struct ast_variable *v, struct ast_variable *alt, int temponly);
static struct iax2_user *build_user(const char *name, struct ast_variable *v, struct ast_variable *alt, int temponly);
static void realtime_update_peer(const char *peername, struct sockaddr_in *sin, time_t regtime);
-static void prune_peers(void);
static void *iax2_dup_variable_datastore(void *);
+static void prune_peers(void);
+static void prune_users(void);
static void iax2_free_variable_datastore(void *);
static int acf_channel_read(struct ast_channel *chan, const char *funcname, char *preparse, char *buf, size_t buflen);
@@ -1380,6 +1381,14 @@ static inline struct iax2_peer *peer_unref(struct iax2_peer *peer)
return NULL;
}
+static struct iax2_user *find_user(const char *name)
+{
+ struct iax2_user tmp_user = {
+ .name = name,
+ };
+
+ return ao2_find(users, &tmp_user, OBJ_POINTER);
+}
static inline struct iax2_user *user_ref(struct iax2_user *user)
{
ao2_ref(user, +1);
@@ -2525,7 +2534,8 @@ static int attempt_transmit(const void *data)
static char *handle_cli_iax2_prune_realtime(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
{
- struct iax2_peer *peer;
+ struct iax2_peer *peer = NULL;
+ struct iax2_user *user = NULL;
switch (cmd) {
case CLI_INIT:
@@ -2539,25 +2549,40 @@ static char *handle_cli_iax2_prune_realtime(struct ast_cli_entry *e, int cmd, st
return complete_iax2_peers(a->line, a->word, a->pos, a->n);
return NULL;
}
-
if (a->argc != 4)
return CLI_SHOWUSAGE;
if (!strcmp(a->argv[3], "all")) {
- reload_config();
+ prune_users();
+ prune_peers();
ast_cli(a->fd, "Cache flushed successfully.\n");
- } else if ((peer = find_peer(a->argv[3], 0))) {
- if(ast_test_flag(peer, IAX_RTCACHEFRIENDS)) {
- ast_set_flag(peer, IAX_RTAUTOCLEAR);
- expire_registry(peer_ref(peer));
- ast_cli(a->fd, "Peer %s was removed from the cache.\n", a->argv[3]);
- } else {
- ast_cli(a->fd, "Peer %s is not eligible for this operation.\n", a->argv[3]);
+ }
+ peer = find_peer(a->argv[3], 0);
+ user = find_user(a->argv[3]);
+ if (peer || user) {
+ if (peer) {
+ if (ast_test_flag(peer, IAX_RTCACHEFRIENDS)) {
+ ast_set_flag(peer, IAX_RTAUTOCLEAR);
+ expire_registry(peer_ref(peer));
+ ast_cli(a->fd, "Peer %s was removed from the cache.\n", a->argv[3]);
+ } else {
+ ast_cli(a->fd, "Peer %s is not eligible for this operation.\n", a->argv[3]);
+ }
+ peer_unref(peer);
+ }
+ if (user) {
+ if (ast_test_flag(user, IAX_RTCACHEFRIENDS)) {
+ ast_set_flag(user, IAX_RTAUTOCLEAR);
+ ast_cli(a->fd, "User %s was removed from the cache.\n", a->argv[3]);
+ } else {
+ ast_cli(a->fd, "User %s is not eligible for this operation.\n", a->argv[3]);
+ }
+ ao2_unlink(users,user);
+ user_unref(user);
}
- peer_unref(peer);
} else {
- ast_cli(a->fd, "Peer %s was not found in the cache.\n", a->argv[3]);
+ ast_cli(a->fd, "%s was not found in the cache.\n", a->argv[3]);
}
-
+
return CLI_SUCCESS;
}
@@ -11020,8 +11045,9 @@ static void prune_users(void)
i = ao2_iterator_init(users, 0);
while ((user = ao2_iterator_next(&i))) {
- if (ast_test_flag(user, IAX_DELME))
+ if (ast_test_flag(user, IAX_DELME) || ast_test_flag(user, IAX_RTCACHEFRIENDS)) {
ao2_unlink(users, user);
+ }
user_unref(user);
}
}
@@ -11034,8 +11060,9 @@ static void prune_peers(void)
i = ao2_iterator_init(peers, 0);
while ((peer = ao2_iterator_next(&i))) {
- if (ast_test_flag(peer, IAX_DELME))
+ if (ast_test_flag(peer, IAX_DELME) || ast_test_flag(peer, IAX_RTCACHEFRIENDS)) {
unlink_peer(peer);
+ }
peer_unref(peer);
}
}