]> git.ipfire.org Git - thirdparty/asterisk.git/commitdiff
Add a control frame to indicate the source of media has changed. Depending on the...
authorJoshua Colp <jcolp@digium.com>
Wed, 5 Mar 2008 22:32:10 +0000 (22:32 +0000)
committerJoshua Colp <jcolp@digium.com>
Wed, 5 Mar 2008 22:32:10 +0000 (22:32 +0000)
(closes issue #12148)
Reported by: jcomellas

git-svn-id: https://origsvn.digium.com/svn/asterisk/branches/1.4@106235 65c4cc65-6c06-0410-ace0-fbb531ad65f3

15 files changed:
apps/app_dial.c
apps/app_followme.c
channels/chan_alsa.c
channels/chan_h323.c
channels/chan_mgcp.c
channels/chan_oss.c
channels/chan_phone.c
channels/chan_sip.c
channels/chan_skinny.c
channels/chan_zap.c
include/asterisk/frame.h
main/channel.c
main/dial.c
main/file.c
main/rtp.c

index 4cf7153cbac3878cb8b083e2158f1f6812aac97a..2465bfc1d6b72f511de1a6a21975df79f47c6f2d 100644 (file)
@@ -635,6 +635,11 @@ static struct ast_channel *wait_for_answer(struct ast_channel *in, struct dial_l
                                                ast_verbose (VERBOSE_PREFIX_3 "%s requested a video update, passing it to %s\n", c->name, in->name);
                                        ast_indicate(in, AST_CONTROL_VIDUPDATE);
                                        break;
+                               case AST_CONTROL_SRCUPDATE:
+                                       if (option_verbose > 2)
+                                               ast_verbose (VERBOSE_PREFIX_3 "%s requested a source update, passing it to %s\n", c->name, in->name);
+                                       ast_indicate(in, AST_CONTROL_SRCUPDATE);
+                                       break;
                                case AST_CONTROL_PROCEEDING:
                                        if (option_verbose > 2)
                                                ast_verbose (VERBOSE_PREFIX_3 "%s is proceeding passing it to %s\n", c->name, in->name);
@@ -745,7 +750,8 @@ static struct ast_channel *wait_for_answer(struct ast_channel *in, struct dial_l
                        if (single && (f->frametype == AST_FRAME_CONTROL) && 
                                ((f->subclass == AST_CONTROL_HOLD) || 
                                 (f->subclass == AST_CONTROL_UNHOLD) || 
-                                (f->subclass == AST_CONTROL_VIDUPDATE))) {
+                                (f->subclass == AST_CONTROL_VIDUPDATE) ||
+                                (f->subclass == AST_CONTROL_SRCUPDATE))) {
                                if (option_verbose > 2)
                                        ast_verbose(VERBOSE_PREFIX_3 "%s requested special control %d, passing it to %s\n", in->name, f->subclass, outgoing->chan->name);
                                ast_indicate_data(outgoing->chan, f->subclass, f->data, f->datalen);
index cd79cc3080b6b2fa9e1f5bcce84556d12312dedd..78f5c70cf4b13ea1ad2897015b0dfe9f4d314997 100644 (file)
@@ -673,6 +673,10 @@ static struct ast_channel *wait_for_winner(struct findme_user_listptr *findme_us
                                                        if (option_verbose > 2)
                                                                ast_verbose ( VERBOSE_PREFIX_3 "%s requested a video update, passing it to %s\n", winner->name, caller->name);
                                                        break;
+                                               case AST_CONTROL_SRCUPDATE:
+                                                       if (option_verbose > 2)
+                                                               ast_verbose ( VERBOSE_PREFIX_3 "%s requested a source update, passing it to %s\n", winner->name, caller->name);
+                                                       break;
                                                case AST_CONTROL_PROCEEDING:
                                                        if (option_verbose > 2)
                                                                ast_verbose ( VERBOSE_PREFIX_3 "%s is proceeding passing it to %s\n", winner->name,caller->name);
index 79bc313cd6f999ad213c6ed530152d34f5672fb6..9a416837bccb6f0f63177364798ca7fb3cfc033d 100644 (file)
@@ -743,32 +743,34 @@ static int alsa_indicate(struct ast_channel *chan, int cond, const void *data, s
        ast_mutex_lock(&alsalock);
 
        switch (cond) {
-               case AST_CONTROL_BUSY:
-                       res = 1;
-                       break;
-               case AST_CONTROL_CONGESTION:
-                       res = 2;
-                       break;
-               case AST_CONTROL_RINGING:
-               case AST_CONTROL_PROGRESS:
-                       break;
-               case -1:
-                       res = -1;
-                       break;
-               case AST_CONTROL_VIDUPDATE:
-                       res = -1;
-                       break;
-               case AST_CONTROL_HOLD:
-                       ast_verbose(" << Console Has Been Placed on Hold >> \n");
-                       ast_moh_start(chan, data, mohinterpret);
-                       break;
-               case AST_CONTROL_UNHOLD:
-                       ast_verbose(" << Console Has Been Retrieved from Hold >> \n");
-                       ast_moh_stop(chan);
-                       break;
-               default:
-                       ast_log(LOG_WARNING, "Don't know how to display condition %d on %s\n", cond, chan->name);
-                       res = -1;
+       case AST_CONTROL_BUSY:
+               res = 1;
+               break;
+       case AST_CONTROL_CONGESTION:
+               res = 2;
+               break;
+       case AST_CONTROL_RINGING:
+       case AST_CONTROL_PROGRESS:
+               break;
+       case -1:
+               res = -1;
+               break;
+       case AST_CONTROL_VIDUPDATE:
+               res = -1;
+               break;
+       case AST_CONTROL_HOLD:
+               ast_verbose(" << Console Has Been Placed on Hold >> \n");
+               ast_moh_start(chan, data, mohinterpret);
+               break;
+       case AST_CONTROL_UNHOLD:
+               ast_verbose(" << Console Has Been Retrieved from Hold >> \n");
+               ast_moh_stop(chan);
+               break;
+       case AST_CONTROL_SRCUPDATE:
+               break;
+       default:
+               ast_log(LOG_WARNING, "Don't know how to display condition %d on %s\n", cond, chan->name);
+               res = -1;
        }
 
        if (res > -1)
index fb0d8315f01cfbd0a9e35fee8b19f9ff1a9886f0..57dbf80652e04a005f6aa70a0f32aca3c3dd5696 100644 (file)
@@ -915,6 +915,10 @@ static int oh323_indicate(struct ast_channel *c, int condition, const void *data
                ast_moh_stop(c);
                res = 0;
                break;
+       case AST_CONTROL_SRCUPDATE:
+               ast_rtp_new_source(pvt->rtp);
+               res = 0;
+               break;
        case AST_CONTROL_PROCEEDING:
        case -1:
                break;
index 353877285da6473d25957ea0d6758a2acc822139..bd57e54f3f49932ae55638b8ea195d6e35d8ac35 100644 (file)
@@ -1445,6 +1445,9 @@ static int mgcp_indicate(struct ast_channel *ast, int ind, const void *data, siz
        case AST_CONTROL_UNHOLD:
                ast_moh_stop(ast);
                break;
+       case AST_CONTROL_SRCUPDATE:
+               ast_rtp_new_source(sub->rtp);
+               break;
        case -1:
                transmit_notify_request(sub, "");
                break;
index 7b3c8875173960a6c5687e3e08e62ebb60b5d1d4..0820c4b7feb6eec4fe9d45f84c499cb0dbf6f115 100644 (file)
@@ -951,32 +951,33 @@ static int oss_indicate(struct ast_channel *c, int cond, const void *data, size_
        int res = -1;
 
        switch (cond) {
-               case AST_CONTROL_BUSY:
-               case AST_CONTROL_CONGESTION:
-               case AST_CONTROL_RINGING:
+       case AST_CONTROL_BUSY:
+       case AST_CONTROL_CONGESTION:
+       case AST_CONTROL_RINGING:
                        res = cond;
                        break;
-
-               case -1:
-                       o->cursound = -1;
-                       o->nosound = 0;         /* when cursound is -1 nosound must be 0 */
-                       return 0;
-
-               case AST_CONTROL_VIDUPDATE:
-                       res = -1;
-                       break;
-               case AST_CONTROL_HOLD:
-                       ast_verbose(" << Console Has Been Placed on Hold >> \n");
-                       ast_moh_start(c, data, o->mohinterpret);
-                       break;
-               case AST_CONTROL_UNHOLD:
-                       ast_verbose(" << Console Has Been Retrieved from Hold >> \n");
-                       ast_moh_stop(c);
+                       
+       case -1:
+               o->cursound = -1;
+               o->nosound = 0;         /* when cursound is -1 nosound must be 0 */
+               return 0;
+               
+       case AST_CONTROL_VIDUPDATE:
+               res = -1;
+               break;
+       case AST_CONTROL_HOLD:
+               ast_verbose(" << Console Has Been Placed on Hold >> \n");
+               ast_moh_start(c, data, o->mohinterpret);
                        break;
-
-               default:
-                       ast_log(LOG_WARNING, "Don't know how to display condition %d on %s\n", cond, c->name);
-                       return -1;
+       case AST_CONTROL_UNHOLD:
+               ast_verbose(" << Console Has Been Retrieved from Hold >> \n");
+               ast_moh_stop(c);
+               break;
+       case AST_CONTROL_SRCUPDATE:
+               break;
+       default:
+               ast_log(LOG_WARNING, "Don't know how to display condition %d on %s\n", cond, c->name);
+               return -1;
        }
 
        if (res > -1)
index ad34d23298b47ad1c2309547e59ab211a3792718..b551b1cba703eb2f66ab38b9a8e06ad9e1be52c3 100644 (file)
@@ -213,21 +213,24 @@ static int phone_indicate(struct ast_channel *chan, int condition, const void *d
        int res=-1;
        ast_log(LOG_DEBUG, "Requested indication %d on channel %s\n", condition, chan->name);
        switch(condition) {
-               case AST_CONTROL_FLASH:
-                       ioctl(p->fd, IXJCTL_PSTN_SET_STATE, PSTN_ON_HOOK);
-                       usleep(320000);
-                       ioctl(p->fd, IXJCTL_PSTN_SET_STATE, PSTN_OFF_HOOK);
+       case AST_CONTROL_FLASH:
+               ioctl(p->fd, IXJCTL_PSTN_SET_STATE, PSTN_ON_HOOK);
+               usleep(320000);
+               ioctl(p->fd, IXJCTL_PSTN_SET_STATE, PSTN_OFF_HOOK);
                        p->lastformat = -1;
                        res = 0;
                        break;
-               case AST_CONTROL_HOLD:
-                       ast_moh_start(chan, data, NULL);
-                       break;
-               case AST_CONTROL_UNHOLD:
-                       ast_moh_stop(chan);
-                       break;
-               default:
-                       ast_log(LOG_WARNING, "Condition %d is not supported on channel %s\n", condition, chan->name);
+       case AST_CONTROL_HOLD:
+               ast_moh_start(chan, data, NULL);
+               break;
+       case AST_CONTROL_UNHOLD:
+               ast_moh_stop(chan);
+               break;
+       case AST_CONTROL_SRCUPDATE:
+               res = 0;
+               break;
+       default:
+               ast_log(LOG_WARNING, "Condition %d is not supported on channel %s\n", condition, chan->name);
        }
        return res;
 }
index 48dc39e4a07cde35626f5e766d07c21175bf1317..fe1f4bc3b624b6da9d3a9e7ba691e2917ebcd78e 100644 (file)
@@ -3663,7 +3663,6 @@ static int sip_answer(struct ast_channel *ast)
                                ast_log(LOG_DEBUG,"T38State change to %d on channel %s\n", p->t38.state, ast->name);
                        res = transmit_response_with_t38_sdp(p, "200 OK", &p->initreq, XMIT_CRITICAL);
                } else {
-                       ast_rtp_new_source(p->rtp);
                        res = transmit_response_with_sdp(p, "200 OK", &p->initreq, XMIT_CRITICAL);
                }
        }
@@ -3938,6 +3937,9 @@ static int sip_indicate(struct ast_channel *ast, int condition, const void *data
                } else
                        res = -1;
                break;
+       case AST_CONTROL_SRCUPDATE:
+               ast_rtp_new_source(p->rtp);
+               break;
        case -1:
                res = -1;
                break;
index c712e3d947cac969644e6779cd6c93ff9d1a4c3c..2e160c865a2ab071a255776248694996386cbf52 100644 (file)
@@ -2794,6 +2794,9 @@ static int skinny_indicate(struct ast_channel *ast, int ind, const void *data, s
                break;
        case AST_CONTROL_PROCEEDING:
                break;
+       case AST_CONTROL_SRCUPDATE:
+               ast_rtp_new_source(sub->rtp);
+               break;
        default:
                ast_log(LOG_WARNING, "Don't know how to indicate condition %d\n", ind);
                return -1;
index 42757fb5ce3944d820a2fbe850a17ff5d95e244f..0c33f628634e7dfec6e9a946253b2afbb05fb187 100644 (file)
@@ -5186,6 +5186,9 @@ static int zt_indicate(struct ast_channel *chan, int condition, const void *data
                        } else
                                res = 0;
                        break;
+               case AST_CONTROL_SRCUPDATE:
+                       res = 0;
+                       break;
                case -1:
                        res = tone_zone_play_tone(p->subs[index].zfd, -1);
                        break;
index 3f15430280084f4602c61350f8857d5c6c5e1398..9165b34e8a83a85b9ac3e56d676f67dc1debfc1e 100644 (file)
@@ -85,6 +85,7 @@ struct ast_codec_pref {
        \arg \b HOLD    Call is placed on hold
        \arg \b UNHOLD  Call is back from hold
        \arg \b VIDUPDATE       Video update requested
+       \arg \b SRCUPDATE       The source of media has changed
 
 */
 
@@ -290,6 +291,7 @@ enum ast_control_frame_type {
        AST_CONTROL_HOLD = 16,          /*!< Indicate call is placed on hold */
        AST_CONTROL_UNHOLD = 17,        /*!< Indicate call is left from hold */
        AST_CONTROL_VIDUPDATE = 18,     /*!< Indicate video frame update */
+       AST_CONTROL_SRCUPDATE = 20,     /*!< Indicate source of media has changed */
 };
 
 #define AST_SMOOTHER_FLAG_G729         (1 << 0)
index 16881a3d5575c23f82ec36de88cf333bfd782016..73c7db60385227ce96f3d790db9638290df2ee41 100644 (file)
@@ -2372,6 +2372,8 @@ int ast_indicate_data(struct ast_channel *chan, int condition, const void *data,
                                /* Do nothing.... */
                        } else if (condition == AST_CONTROL_VIDUPDATE) {
                                /* Do nothing.... */
+                       } else if (condition == AST_CONTROL_SRCUPDATE) {
+                               /* Do nothing... */
                        } else {
                                /* not handled */
                                ast_log(LOG_WARNING, "Unable to handle indication %d for '%s'\n", condition, chan->name);
@@ -2890,6 +2892,7 @@ struct ast_channel *__ast_request_and_dial(const char *type, int format, void *d
                                case AST_CONTROL_HOLD:
                                case AST_CONTROL_UNHOLD:
                                case AST_CONTROL_VIDUPDATE:
+                               case AST_CONTROL_SRCUPDATE:
                                case -1:                        /* Ignore -- just stopping indications */
                                        break;
 
@@ -3774,6 +3777,7 @@ static enum ast_bridge_result ast_generic_bridge(struct ast_channel *c0, struct
                        case AST_CONTROL_HOLD:
                        case AST_CONTROL_UNHOLD:
                        case AST_CONTROL_VIDUPDATE:
+                       case AST_CONTROL_SRCUPDATE:
                                ast_indicate_data(other, f->subclass, f->data, f->datalen);
                                break;
                        default:
@@ -3907,6 +3911,10 @@ enum ast_bridge_result ast_channel_bridge(struct ast_channel *c0, struct ast_cha
        if (!c1->tech->send_digit_begin)
                ast_set_flag(c0, AST_FLAG_END_DTMF_ONLY);
 
+       /* Before we enter in and bridge these two together tell them both the source of audio has changed */
+       ast_indicate(c0, AST_CONTROL_SRCUPDATE);
+       ast_indicate(c1, AST_CONTROL_SRCUPDATE);
+
        for (/* ever */;;) {
                struct timeval now = { 0, };
                int to;
@@ -4070,6 +4078,10 @@ enum ast_bridge_result ast_channel_bridge(struct ast_channel *c0, struct ast_cha
        ast_clear_flag(c0, AST_FLAG_END_DTMF_ONLY);
        ast_clear_flag(c1, AST_FLAG_END_DTMF_ONLY);
 
+       /* Now that we have broken the bridge the source will change yet again */
+       ast_indicate(c0, AST_CONTROL_SRCUPDATE);
+       ast_indicate(c1, AST_CONTROL_SRCUPDATE);
+
        c0->_bridge = NULL;
        c1->_bridge = NULL;
 
index 807ba12c3b017167eec5ed474616878b84419f2c..e96e776dee1a5f8eafb7266c84839140d9e148a9 100644 (file)
@@ -358,6 +358,10 @@ static void handle_frame(struct ast_dial *dial, struct ast_dial_channel *channel
                                ast_verbose (VERBOSE_PREFIX_3 "%s requested a video update, passing it to %s\n", channel->owner->name, chan->name);
                        ast_indicate(chan, AST_CONTROL_VIDUPDATE);
                        break;
+               case AST_CONTROL_SRCUPDATE:
+                       if (option_verbose > 2)
+                               ast_verbose (VERBOSE_PREFIX_3 "%s requested a source update, passing it to %s\n", channel->owner->name, chan->name);
+                       ast_indicate(chan, AST_CONTROL_SRCUPDATE);
                case AST_CONTROL_PROCEEDING:
                        if (option_verbose > 2)
                                ast_verbose (VERBOSE_PREFIX_3 "%s is proceeding, passing it to %s\n", channel->owner->name, chan->name);
index c1ff4c39a6b2fc98ad8a2f57b90e8354eeec4df1..809eb43c0ecd8aaae0f9ca28101ece40e751f08f 100644 (file)
@@ -1159,6 +1159,7 @@ static int waitstream_core(struct ast_channel *c, const char *breakon,
                                case AST_CONTROL_RINGING:
                                case AST_CONTROL_ANSWER:
                                case AST_CONTROL_VIDUPDATE:
+                               case AST_CONTROL_SRCUPDATE:
                                case AST_CONTROL_HOLD:
                                case AST_CONTROL_UNHOLD:
                                        /* Unimportant */
index 6578c400e49a96ca2bdec018ded2522138ed0c21..b5864f916a49487b547fed694f03a8e640eaab5e 100644 (file)
@@ -2968,7 +2968,8 @@ static enum ast_bridge_result bridge_native_loop(struct ast_channel *c0, struct
                } else if ((fr->frametype == AST_FRAME_CONTROL) && !(flags & AST_BRIDGE_IGNORE_SIGS)) {
                        if ((fr->subclass == AST_CONTROL_HOLD) ||
                            (fr->subclass == AST_CONTROL_UNHOLD) ||
-                           (fr->subclass == AST_CONTROL_VIDUPDATE)) {
+                           (fr->subclass == AST_CONTROL_VIDUPDATE) ||
+                           (fr->subclass == AST_CONTROL_SRCUPDATE)) {
                                if (fr->subclass == AST_CONTROL_HOLD) {
                                        /* If we someone went on hold we want the other side to reinvite back to us */
                                        if (who == c0)
@@ -3199,7 +3200,8 @@ static enum ast_bridge_result bridge_p2p_loop(struct ast_channel *c0, struct ast
                } else if ((fr->frametype == AST_FRAME_CONTROL) && !(flags & AST_BRIDGE_IGNORE_SIGS)) {
                        if ((fr->subclass == AST_CONTROL_HOLD) ||
                            (fr->subclass == AST_CONTROL_UNHOLD) ||
-                           (fr->subclass == AST_CONTROL_VIDUPDATE)) {
+                           (fr->subclass == AST_CONTROL_VIDUPDATE) ||
+                           (fr->subclass == AST_CONTROL_SRCUPDATE)) {
                                /* If we are going on hold, then break callback mode and P2P bridging */
                                if (fr->subclass == AST_CONTROL_HOLD) {
                                        if (p0_callback)