]> git.ipfire.org Git - thirdparty/asterisk.git/commitdiff
bridge.c: Obey BRIDGE_NOANSWER variable to skip answering channel.
authorNaveen Albert <asterisk@phreaknet.org>
Thu, 14 Aug 2025 12:50:31 +0000 (08:50 -0400)
committerNaveen Albert <asterisk@phreaknet.org>
Fri, 15 Aug 2025 15:59:22 +0000 (15:59 +0000)
If the BRIDGE_NOANSWER variable is set on a channel, it is not supposed
to answer when another channel bridges to it using Bridge(), and this is
checked when ast_bridge_call* is called. However, another path exists
(bridge_exec -> ast_bridge_add_channel) where this variable was not
checked and channels would be answered. We now check the variable there.

Resolves: #401
Resolves: #1364

main/bridge.c
main/features.c

index 46526aea07b13d6ce881734ff4952d5fb048e139..cc2183b5268f64021fd3e3d92dfd6c6f32b17a9c 100644 (file)
@@ -2578,6 +2578,8 @@ int ast_bridge_add_channel(struct ast_bridge *bridge, struct ast_channel *chan,
                ast_bridge_unlock(chan_bridge);
                ast_bridge_unlock(bridge);
        } else {
+               int noanswer;
+               const char *value;
                /* Slightly less easy case. We need to yank channel A from
                 * where he currently is and impart him into our bridge.
                 */
@@ -2587,9 +2589,17 @@ int ast_bridge_add_channel(struct ast_bridge *bridge, struct ast_channel *chan,
                        ast_bridge_features_destroy(features);
                        return -1;
                }
-               if (ast_channel_state(yanked_chan) != AST_STATE_UP) {
+
+               ast_channel_lock(chan);
+               value = pbx_builtin_getvar_helper(chan, "BRIDGE_NOANSWER");
+               noanswer = !ast_strlen_zero(value) ? 1 : 0;
+               ast_channel_unlock(chan);
+               if (noanswer) {
+                       ast_debug(3, "Skipping answer on bridge target channel %s\n", ast_channel_name(chan));
+               } else if (ast_channel_state(yanked_chan) != AST_STATE_UP) {
                        ast_answer(yanked_chan);
                }
+
                ast_channel_ref(yanked_chan);
                if (ast_bridge_impart(bridge, yanked_chan, NULL, features,
                        AST_BRIDGE_IMPART_CHAN_INDEPENDENT)) {
index 547fdc15e1c9e14c17adaa1f3003ab61a47cce4f..6f9cab935956f110524d60e4572f4aa4e9b699e6 100644 (file)
                                                <para>Additionally, to prevent a bridged channel (the target of the Bridge application)
                                                from answering, the <literal>BRIDGE_NOANSWER</literal> variable can be set to inhibit
                                                answering.</para>
+                                               <warning><para>Do not set the <literal>BRIDGE_NOANSWER</literal> variable globally,
+                                               as it will break normal bridging behavior in many cases. Only use this variable on
+                                               a per-channel basis when you really know what you are doing!</para></warning>
                                        </option>
                                        <option name="S(x)">
                                                <para>Hang up the call after <replaceable>x</replaceable> seconds *after* the called party has answered the call.</para>