summaryrefslogtreecommitdiff
path: root/apps/app_queue.c
diff options
context:
space:
mode:
authorRichard Mudgett <rmudgett@digium.com>2015-09-24 14:56:24 -0500
committerRichard Mudgett <rmudgett@digium.com>2015-09-25 12:31:38 -0500
commit6b1e7583c150cc9bafcb567c789b6c23c60e2c71 (patch)
tree3540aeb38cd2a945f14eba573e8e839e887de105 /apps/app_queue.c
parent6bf304bf251e31ab7c7a4d89508445b84fb5d551 (diff)
app_queue.c: Force COLP update if outgoing channel name changed.
* When a call is answered and the outgoing channel name has changed then force a connected line update because the channel is no longer the same. The channel was masqueraded into by another channel. This is usually because of a call pickup. Note: Forwarded calls are handled in a controlled manner so the original channel name is replaced with the forwarded channel. ASTERISK-25423 #close Reported by: John Hardin Change-Id: Ie275ea9e99c092ad369db23e0feb08c44498c172
Diffstat (limited to 'apps/app_queue.c')
-rw-r--r--apps/app_queue.c27
1 files changed, 25 insertions, 2 deletions
diff --git a/apps/app_queue.c b/apps/app_queue.c
index 2ca3a9e8e..6dfb14356 100644
--- a/apps/app_queue.c
+++ b/apps/app_queue.c
@@ -1446,6 +1446,8 @@ struct callattempt {
/*! TRUE if the call is still active */
unsigned int stillgoing:1;
struct ast_aoc_decoded *aoc_s_rate_list;
+ /*! Original channel name. Must be freed. Could be NULL if allocation failed. */
+ char *orig_chan_name;
};
@@ -3951,6 +3953,7 @@ static void callattempt_free(struct callattempt *doomed)
ao2_ref(doomed->member, -1);
}
ast_party_connected_line_free(&doomed->connected);
+ ast_free(doomed->orig_chan_name);
ast_free(doomed);
}
@@ -4282,6 +4285,9 @@ static int ring_entry(struct queue_ent *qe, struct callattempt *tmp, int *busies
ast_channel_exten_set(tmp->chan, ast_channel_exten(qe->chan));
}
+ /* Save the original channel name to detect call pickup masquerading in. */
+ tmp->orig_chan_name = ast_strdup(ast_channel_name(tmp->chan));
+
ast_channel_unlock(tmp->chan);
ast_channel_unlock(qe->chan);
@@ -4703,7 +4709,14 @@ static struct callattempt *wait_for_answer(struct queue_ent *qe, struct callatte
if (o->stillgoing && (o->chan) && (ast_channel_state(o->chan) == AST_STATE_UP)) {
if (!peer) {
ast_verb(3, "%s answered %s\n", ochan_name, inchan_name);
- if (!o->block_connected_update) {
+ if (o->orig_chan_name
+ && strcmp(o->orig_chan_name, ochan_name)) {
+ /*
+ * The channel name changed so we must generate COLP update.
+ * Likely because a call pickup channel masqueraded in.
+ */
+ update_connected_line_from_peer(in, o->chan, 1);
+ } else if (!o->block_connected_update) {
if (o->pending_connected_update) {
if (ast_channel_connected_line_sub(o->chan, in, &o->connected, 0) &&
ast_channel_connected_line_macro(o->chan, in, &o->connected, 1, 0)) {
@@ -4791,6 +4804,9 @@ static struct callattempt *wait_for_answer(struct queue_ent *qe, struct callatte
ast_party_connected_line_copy(&o->connected, ast_channel_connected(in));
}
+ ast_free(o->orig_chan_name);
+ o->orig_chan_name = ast_strdup(ast_channel_name(o->chan));
+
ast_channel_req_accountcodes(o->chan, in, AST_CHANNEL_REQUESTOR_BRIDGE_PEER);
if (!ast_channel_redirecting(o->chan)->from.number.valid
@@ -4866,7 +4882,14 @@ static struct callattempt *wait_for_answer(struct queue_ent *qe, struct callatte
ast_verb(3, "%s answered %s\n", ochan_name, inchan_name);
ast_channel_publish_dial(qe->chan, o->chan, on, "ANSWER");
publish_dial_end_event(qe->chan, outgoing, o->chan, "CANCEL");
- if (!o->block_connected_update) {
+ if (o->orig_chan_name
+ && strcmp(o->orig_chan_name, ochan_name)) {
+ /*
+ * The channel name changed so we must generate COLP update.
+ * Likely because a call pickup channel masqueraded in.
+ */
+ update_connected_line_from_peer(in, o->chan, 1);
+ } else if (!o->block_connected_update) {
if (o->pending_connected_update) {
if (ast_channel_connected_line_sub(o->chan, in, &o->connected, 0) &&
ast_channel_connected_line_macro(o->chan, in, &o->connected, 1, 0)) {