From 1eea29a474562cf5f0e949d48e07308590533efb Mon Sep 17 00:00:00 2001 From: Anthony Minessale Date: Tue, 25 Nov 2008 17:53:35 +0000 Subject: [PATCH] update git-svn-id: http://svn.freeswitch.org/svn/freeswitch/trunk@10533 d0543943-73ff-0310-b7d9-9358b9ac24b2 --- src/include/switch_rtp.h | 2 + src/include/switch_types.h | 5 ++- .../applications/mod_commands/mod_commands.c | 4 +- src/mod/endpoints/mod_sofia/mod_sofia.c | 18 ++------- src/switch_core_state_machine.c | 8 +--- src/switch_ivr_bridge.c | 29 +++++++------- src/switch_rtp.c | 39 +++++++++++++++++++ 7 files changed, 68 insertions(+), 37 deletions(-) diff --git a/src/include/switch_rtp.h b/src/include/switch_rtp.h index 03141d51eb..3658e01355 100644 --- a/src/include/switch_rtp.h +++ b/src/include/switch_rtp.h @@ -351,6 +351,8 @@ SWITCH_DECLARE(switch_status_t) switch_rtp_zerocopy_read(switch_rtp_t *rtp_sessi */ SWITCH_DECLARE(switch_status_t) switch_rtp_zerocopy_read_frame(switch_rtp_t *rtp_session, switch_frame_t *frame, switch_io_flag_t io_flags); +SWITCH_DECLARE(void) rtp_flush_read_buffer(switch_rtp_t *rtp_session); + /*! \brief Enable VAD on an RTP Session \param rtp_session the RTP session diff --git a/src/include/switch_types.h b/src/include/switch_types.h index 22375eb087..97bc4ef98d 100644 --- a/src/include/switch_types.h +++ b/src/include/switch_types.h @@ -568,6 +568,7 @@ typedef enum { SWITCH_MESSAGE_INDICATE_VIDEO_REFRESH_REQ, SWITCH_MESSAGE_INDICATE_DISPLAY, SWITCH_MESSAGE_INDICATE_TRANSCODING_NECESSARY, + SWITCH_MESSAGE_INDICATE_AUDIO_SYNC, SWITCH_MESSAGE_INVALID } switch_core_session_message_types_t; @@ -742,7 +743,7 @@ CF_CONTROLLED = (1 << 12) - Channel is under control CF_PROXY_MODE = (1 << 13) - Channel has no media CF_SUSPEND = (1 << 14) - Suspend i/o CF_EVENT_PARSE = (1 << 15) - Suspend control events -CF_REPEAT_STATE = (1 << 16) - Tell the state machine to repeat a state +CF_USE_ME = (1 << 16) - use me CF_GEN_RINGBACK = (1 << 17) - Channel is generating it's own ringback CF_RING_READY = (1 << 18) - Channel is ready to send ringback CF_BREAK = (1 << 19) - Channel should stop what it's doing @@ -773,7 +774,7 @@ typedef enum { CF_PROXY_MODE = (1 << 13), CF_SUSPEND = (1 << 14), CF_EVENT_PARSE = (1 << 15), - CF_REPEAT_STATE = (1 << 16), + CF_USE_ME = (1 << 16), CF_GEN_RINGBACK = (1 << 17), CF_RING_READY = (1 << 18), CF_BREAK = (1 << 19), diff --git a/src/mod/applications/mod_commands/mod_commands.c b/src/mod/applications/mod_commands/mod_commands.c index 20f8fa8690..05117a4573 100644 --- a/src/mod/applications/mod_commands/mod_commands.c +++ b/src/mod/applications/mod_commands/mod_commands.c @@ -1127,8 +1127,8 @@ SWITCH_STANDARD_API(transfer_function) } else if (!strcasecmp(arg, "both")) { if (uuid && (other_session = switch_core_session_locate(uuid))) { switch_channel_t *other_channel = switch_core_session_get_channel(other_session); - switch_channel_set_flag(other_channel, CF_TRANSFER); - switch_channel_set_flag(channel, CF_TRANSFER); + switch_channel_set_flag(other_channel, CF_REDIRECT); + switch_channel_set_flag(channel, CF_REDIRECT); switch_ivr_session_transfer(other_session, dest, dp, context); switch_core_session_rwunlock(other_session); } diff --git a/src/mod/endpoints/mod_sofia/mod_sofia.c b/src/mod/endpoints/mod_sofia/mod_sofia.c index ffab3d2a62..25a5899ac5 100644 --- a/src/mod/endpoints/mod_sofia/mod_sofia.c +++ b/src/mod/endpoints/mod_sofia/mod_sofia.c @@ -936,21 +936,11 @@ static switch_status_t sofia_receive_message(switch_core_session_t *session, swi goto end; case SWITCH_MESSAGE_INDICATE_BRIDGE: - /* - if (tech_pvt->rtp_session && switch_test_flag(tech_pvt, TFLAG_TIMER)) { - switch_rtp_clear_flag(tech_pvt->rtp_session, SWITCH_RTP_FLAG_USE_TIMER); - switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "De-activate timed RTP!\n"); - } - */ - goto end; - case SWITCH_MESSAGE_INDICATE_UNBRIDGE: - /* - if (tech_pvt->rtp_session && switch_test_flag(tech_pvt, TFLAG_TIMER)) { - switch_rtp_set_flag(tech_pvt->rtp_session, SWITCH_RTP_FLAG_USE_TIMER); - switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Re-activate timed RTP!\n"); - } - */ + case SWITCH_MESSAGE_INDICATE_AUDIO_SYNC: + if (switch_rtp_ready(tech_pvt->rtp_session)) { + rtp_flush_read_buffer(tech_pvt->rtp_session); + } goto end; case SWITCH_MESSAGE_INDICATE_ANSWER: diff --git a/src/switch_core_state_machine.c b/src/switch_core_state_machine.c index 9403a3b9ed..97e2faffa8 100644 --- a/src/switch_core_state_machine.c +++ b/src/switch_core_state_machine.c @@ -360,19 +360,15 @@ SWITCH_DECLARE(void) switch_core_session_run(switch_core_session_t *session) switch_mutex_lock(session->mutex); while ((state = switch_channel_get_state(session->channel)) != CS_DONE) { - uint8_t exception = 0; midstate = state; - if (switch_channel_test_flag(session->channel, CF_REPEAT_STATE)) { - switch_channel_clear_flag(session->channel, CF_REPEAT_STATE); - exception = 1; - } - if (state != switch_channel_get_running_state(session->channel) || state == CS_HANGUP || exception) { + if (state != switch_channel_get_running_state(session->channel) || state == CS_HANGUP) { int index = 0; int proceed = 1; int do_extra_handlers = 1; switch_channel_set_running_state(session->channel, state); switch_channel_clear_flag(session->channel, CF_TRANSFER); + switch_channel_clear_flag(session->channel, CF_REDIRECT); switch (state) { case CS_NEW: /* Just created, Waiting for first instructions */ diff --git a/src/switch_ivr_bridge.c b/src/switch_ivr_bridge.c index c398e34d46..566b2a1883 100644 --- a/src/switch_ivr_bridge.c +++ b/src/switch_ivr_bridge.c @@ -209,11 +209,11 @@ static void *audio_bridge_thread(switch_thread_t *thread, void *obj) goto end_of_bridge_loop; } - if (switch_channel_test_flag(chan_a, CF_TRANSFER) || switch_channel_test_flag(chan_a, CF_REDIRECT)) { + if (switch_channel_test_flag(chan_a, CF_TRANSFER)) { data->clean_exit = 1; } - if (data->clean_exit || switch_channel_test_flag(chan_b, CF_TRANSFER) || switch_channel_test_flag(chan_b, CF_REDIRECT)) { + if (data->clean_exit || switch_channel_test_flag(chan_b, CF_TRANSFER)) { switch_channel_clear_flag(chan_a, CF_HOLD); switch_channel_clear_flag(chan_a, CF_SUSPEND); goto end_of_bridge_loop; @@ -461,15 +461,16 @@ static switch_status_t audio_bridge_on_exchange_media(switch_core_session_t *ses switch_channel_clear_state_handler(channel, &audio_bridge_peer_state_handlers); state = switch_channel_get_state(channel); - + if (state < CS_HANGUP && switch_true(switch_channel_get_variable(channel, SWITCH_PARK_AFTER_BRIDGE_VARIABLE))) { switch_ivr_park_session(session); } else { - if (!switch_channel_test_flag(channel, CF_TRANSFER) && !switch_channel_test_flag(channel, CF_REDIRECT) && bd && !bd->clean_exit && state != CS_PARK && - state != CS_ROUTING && !switch_channel_test_flag(channel, CF_INNER_BRIDGE)) { + if (!switch_channel_test_flag(channel, CF_TRANSFER) && !switch_channel_test_flag(channel, CF_REDIRECT) && bd && !bd->clean_exit + && state != CS_PARK && state != CS_ROUTING && !switch_channel_test_flag(channel, CF_INNER_BRIDGE)) { switch_channel_hangup(channel, SWITCH_CAUSE_NORMAL_CLEARING); - } + } } + if (switch_true(switch_channel_get_variable(channel, SWITCH_COPY_XML_CDR_VARIABLE))) { switch_xml_t cdr; @@ -528,8 +529,6 @@ static switch_status_t uuid_bridge_on_reset(switch_core_session_t *session) switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "%s CUSTOM RESET\n", switch_channel_get_name(channel)); - switch_channel_clear_flag(channel, CF_REDIRECT); - switch_channel_clear_flag(channel, CF_ORIGINATING); if (switch_channel_test_flag(channel, CF_ORIGINATOR)) { @@ -621,9 +620,11 @@ static switch_status_t uuid_bridge_on_soft_execute(switch_core_session_t *sessio } switch_ivr_multi_threaded_bridge(session, other_session, NULL, NULL, NULL); - + state = switch_channel_get_state(channel); - if (!switch_channel_test_flag(channel, CF_TRANSFER) && !switch_channel_test_flag(channel, CF_REDIRECT) && state < CS_HANGUP && state != CS_ROUTING && state != CS_PARK) { + if (!switch_channel_test_flag(channel, CF_TRANSFER) && + !switch_channel_test_flag(channel, CF_REDIRECT) && state < CS_HANGUP + && state != CS_ROUTING && state != CS_PARK) { switch_channel_set_state(channel, CS_EXECUTE); } switch_core_session_rwunlock(other_session); @@ -956,10 +957,12 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_multi_threaded_bridge(switch_core_ses } if (switch_channel_test_flag(caller_channel, CF_REDIRECT)) { - switch_channel_set_state(caller_channel, CS_RESET); + state = switch_channel_get_state(caller_channel); + if (!(state == CS_RESET || state == CS_PARK || state == CS_ROUTING)) { + switch_channel_set_state(caller_channel, CS_RESET); + } } - - + return status; } diff --git a/src/switch_rtp.c b/src/switch_rtp.c index 3735a56b3a..aeddce7f91 100644 --- a/src/switch_rtp.c +++ b/src/switch_rtp.c @@ -1263,6 +1263,40 @@ static void do_2833(switch_rtp_t *rtp_session) } } +SWITCH_DECLARE(void) rtp_flush_read_buffer(switch_rtp_t *rtp_session) +{ + int was_blocking = 0; + switch_size_t bytes; + switch_status_t status; + + if (!switch_rtp_ready(rtp_session)) { + return; + } + + READ_INC(rtp_session); + + if (!switch_test_flag(rtp_session, SWITCH_RTP_FLAG_NOBLOCK)) { + was_blocking = 1; + switch_set_flag_locked(rtp_session, SWITCH_RTP_FLAG_NOBLOCK); + switch_socket_opt_set(rtp_session->sock_input, SWITCH_SO_NONBLOCK, TRUE); + } + + do { + bytes = sizeof(rtp_msg_t); + status = switch_socket_recvfrom(rtp_session->from_addr, rtp_session->sock_input, 0, (void *) &rtp_session->recv_msg, &bytes); + } while(bytes); + + if (was_blocking) { + switch_clear_flag_locked(rtp_session, SWITCH_RTP_FLAG_NOBLOCK); + switch_socket_opt_set(rtp_session->sock_input, SWITCH_SO_NONBLOCK, FALSE); + } + + READ_DEC(rtp_session); + + + +} + #define return_cng_frame() do_cng = 1; goto timer_check static int rtp_common_read(switch_rtp_t *rtp_session, switch_payload_t *payload_type, switch_frame_flag_t *flags, switch_io_flag_t io_flags) @@ -1315,6 +1349,7 @@ static int rtp_common_read(switch_rtp_t *rtp_session, switch_payload_t *payload_ if (switch_test_flag(rtp_session, SWITCH_RTP_FLAG_BREAK)) { switch_clear_flag_locked(rtp_session, SWITCH_RTP_FLAG_BREAK); do_2833(rtp_session); + rtp_flush_read_buffer(rtp_session); bytes = 0; return_cng_frame(); } @@ -1323,6 +1358,10 @@ static int rtp_common_read(switch_rtp_t *rtp_session, switch_payload_t *payload_ continue; } + if (bytes && rtp_session->recv_msg.header.m) { + rtp_flush_read_buffer(rtp_session); + } + if (bytes && switch_test_flag(rtp_session, SWITCH_RTP_FLAG_AUTOADJ) && switch_sockaddr_get_port(rtp_session->from_addr)) { if (++rtp_session->autoadj_tally >= 10) { const char *tx_host;