From 7aa79c7881e891f335da0c627babafb53cb5b972 Mon Sep 17 00:00:00 2001 From: Kinsey Moore Date: Fri, 12 Sep 2014 18:17:44 +0000 Subject: [PATCH] Bridging: Fix bouncing native bridge This fixes a situation in Asterisk 1.8 and 11 where ast_channel_bridge could cause a bouncing native bridge. In the case of the dial_LS_options test, this was a remote RTP bridge which caused the audio path to continually cycle between Asterisk and the remote endpoints generating a large number of SIP messages and delaying the test long enough to cause it to fail (checking timing was part of the test). The root cause was that the code to decide whether to use native bridging was expecting a time-remaining value of 0 to be the default instead of the actual default value of -1. A value of 0 or negative numbers could also be generated by preceding code in some circumstances. Both issues are addressed in this patch. ASTERISK-24211 #close Reported by: Matt Jordan Review: https://reviewboard.asterisk.org/r/3987/ git-svn-id: https://origsvn.digium.com/svn/asterisk/branches/1.8@423006 65c4cc65-6c06-0410-ace0-fbb531ad65f3 --- main/channel.c | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/main/channel.c b/main/channel.c index 91097451d1..95b87cce20 100644 --- a/main/channel.c +++ b/main/channel.c @@ -7605,8 +7605,13 @@ enum ast_bridge_result ast_channel_bridge(struct ast_channel *c0, struct ast_cha if (config->timelimit) { time_left_ms = config->timelimit - ast_tvdiff_ms(now, config->start_time); - if (time_left_ms < to) + if (time_left_ms < 0) { + time_left_ms = 0; + } + + if (time_left_ms < to) { to = time_left_ms; + } if (time_left_ms <= 0) { if (caller_warning && config->end_sound) @@ -7614,7 +7619,7 @@ enum ast_bridge_result ast_channel_bridge(struct ast_channel *c0, struct ast_cha if (callee_warning && config->end_sound) bridge_playfile(c1, c0, config->end_sound, 0); *fo = NULL; - res = 0; + res = AST_BRIDGE_COMPLETE; ast_test_suite_event_notify("BRIDGE_TIMELIMIT", "Channel1: %s\r\nChannel2: %s", c0->name, c1->name); break; } @@ -7657,7 +7662,7 @@ enum ast_bridge_result ast_channel_bridge(struct ast_channel *c0, struct ast_cha if (ast_test_flag(c0, AST_FLAG_ZOMBIE) || ast_check_hangup_locked(c0) || ast_test_flag(c1, AST_FLAG_ZOMBIE) || ast_check_hangup_locked(c1)) { *fo = NULL; - res = 0; + res = AST_BRIDGE_COMPLETE; ast_debug(1, "Bridge stops because we're zombie or need a soft hangup: c0=%s, c1=%s, flags: %s,%s,%s,%s\n", c0->name, c1->name, ast_test_flag(c0, AST_FLAG_ZOMBIE) ? "Yes" : "No", @@ -7673,7 +7678,7 @@ enum ast_bridge_result ast_channel_bridge(struct ast_channel *c0, struct ast_cha if (c0->tech->bridge && /* if < 1 ms remains use generic bridging for accurate timing */ - (!config->timelimit || to > 1000 || to == 0) && + (!config->timelimit || to > 1000 || to == -1) && (c0->tech->bridge == c1->tech->bridge) && !c0->monitor && !c1->monitor && !c0->audiohooks && !c1->audiohooks &&