]> git.ipfire.org Git - thirdparty/freeswitch.git/commitdiff
FS-10328: [freeswitch-core] Add method to allow orphaned B legs during originate...
authorAnthony Minessale <anthm@freeswitch.org>
Thu, 18 May 2017 16:57:37 +0000 (11:57 -0500)
committerAnthony Minessale <anthm@freeswitch.org>
Thu, 18 May 2017 16:58:44 +0000 (11:58 -0500)
src/mod/applications/mod_commands/mod_commands.c
src/switch_ivr_bridge.c
src/switch_ivr_originate.c

index f9dd5cf338b07504f60674783e1ded18fa408f79..ea46c4996b7a3bc300da2fe2e2cb8dfe245e8af1 100644 (file)
@@ -4111,6 +4111,41 @@ SWITCH_STANDARD_API(uuid_send_info_function)
        return SWITCH_STATUS_SUCCESS;
 }
 
+#define XFER_ZOMBIE_SYNTAX "<uuid>"
+SWITCH_STANDARD_API(uuid_xfer_zombie)
+{
+       switch_status_t status = SWITCH_STATUS_FALSE;
+       char *mycmd = NULL, *argv[2] = { 0 };
+       int argc = 0;
+
+       if (!zstr(cmd) && (mycmd = strdup(cmd))) {
+               argc = switch_separate_string(mycmd, ' ', argv, (sizeof(argv) / sizeof(argv[0])));
+       }
+
+       if (argc < 1) {
+               stream->write_function(stream, "-USAGE: %s\n", XFER_ZOMBIE_SYNTAX);
+       } else {
+               switch_core_session_t *lsession = NULL;
+
+               if ((lsession = switch_core_session_locate(argv[0]))) {
+                       switch_channel_t *channel = switch_core_session_get_channel(lsession);
+
+                       switch_channel_set_flag(channel, CF_XFER_ZOMBIE);
+                       status = SWITCH_STATUS_SUCCESS;
+                       switch_core_session_rwunlock(lsession);
+               }
+       }
+
+       if (status == SWITCH_STATUS_SUCCESS) {
+               stream->write_function(stream, "+OK Success\n");
+       } else {
+               stream->write_function(stream, "-ERR Operation Failed\n");
+       }
+
+       switch_safe_free(mycmd);
+
+       return SWITCH_STATUS_SUCCESS;
+}
 
 #define VIDEO_REFRESH_SYNTAX "<uuid>"
 SWITCH_STANDARD_API(uuid_video_refresh_function)
@@ -4129,6 +4164,7 @@ SWITCH_STANDARD_API(uuid_video_refresh_function)
                switch_core_session_t *lsession = NULL;
 
                if ((lsession = switch_core_session_locate(argv[0]))) {
+                       switch_channel_set_flag(switch_core_session_get_channel(lsession), CF_XFER_ZOMBIE);
                        switch_core_session_request_video_refresh(lsession);
                        switch_core_media_gen_key_frame(lsession);
                        status = SWITCH_STATUS_SUCCESS;
@@ -7264,6 +7300,7 @@ SWITCH_MODULE_LOAD_FUNCTION(mod_commands_load)
        SWITCH_ADD_API(commands_api_interface, "uuid_simplify", "Try to cut out of a call path / attended xfer", uuid_simplify_function, SIMPLIFY_SYNTAX);
        SWITCH_ADD_API(commands_api_interface, "uuid_jitterbuffer", "uuid_jitterbuffer", uuid_jitterbuffer_function, JITTERBUFFER_SYNTAX);
        SWITCH_ADD_API(commands_api_interface, "uuid_zombie_exec", "Set zombie_exec flag on the specified uuid", uuid_zombie_exec_function, "<uuid>");
+       SWITCH_ADD_API(commands_api_interface, "uuid_xfer_zombie", "Allow A leg to hangup and continue originating", uuid_xfer_zombie, XFER_ZOMBIE_SYNTAX);
        SWITCH_ADD_API(commands_api_interface, "xml_flush_cache", "Clear xml cache", xml_flush_function, "<id> <key> <val>");
        SWITCH_ADD_API(commands_api_interface, "xml_locate", "Find some xml", xml_locate_function, "[root | <section> <tag> <tag_attr_name> <tag_attr_val>]");
        SWITCH_ADD_API(commands_api_interface, "xml_wrap", "Wrap another api command in xml", xml_wrap_api_function, "<command> <args>");
@@ -7454,6 +7491,7 @@ SWITCH_MODULE_LOAD_FUNCTION(mod_commands_load)
        switch_console_set_complete("add uuid_dual_transfer ::console::list_uuid");
        switch_console_set_complete("add uuid_video_refresh ::console::list_uuid");
        switch_console_set_complete("add uuid_video_bitrate ::console::list_uuid");
+       switch_console_set_complete("add uuid_xfer_zombie ::console::list_uuid");
        switch_console_set_complete("add version");
        switch_console_set_complete("add uuid_warning ::console::list_uuid");
        switch_console_set_complete("add ...");
index bdf60ce338f68dbfb3326f9faf72e9cfda65c0a6..b1890c8811c609727ee6374cb4d6d1851fd97b18 100644 (file)
@@ -886,7 +886,20 @@ static switch_status_t audio_bridge_on_exchange_media(switch_core_session_t *ses
                                switch_channel_hangup(channel, SWITCH_CAUSE_PICKED_OFF);
                        } else {
                                if (!switch_channel_test_flag(channel, CF_ANSWERED)) {
-                                       switch_channel_hangup(channel, SWITCH_CAUSE_ORIGINATOR_CANCEL);
+                                       int x = 0;
+
+                                       if (switch_channel_execute_on(channel, "execute_on_orphaned_bleg") == SWITCH_STATUS_SUCCESS) {
+                                               x++;
+                                       }
+
+                                       if (switch_channel_api_on(channel, "api_on_orphaned_bleg") == SWITCH_STATUS_SUCCESS) {
+                                               x++;
+                                       }
+
+                                       if (!x) {
+                                               switch_channel_hangup(channel, SWITCH_CAUSE_ORIGINATOR_CANCEL);
+                                       }
+                                       
                                } else {
                                        switch_channel_hangup(channel, SWITCH_CAUSE_NORMAL_CLEARING);
                                }
index 28f1f2bc06ba90ead11dded1647b280da7e5c9d4..0cb8d03e07ab7369c8c305266dc5bbacca84453b 100644 (file)
@@ -2179,6 +2179,12 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_originate(switch_core_session_t *sess
                const char *cdr_var;
                const char *json_cdr_var;
 
+               if (switch_channel_var_true(caller_channel, "originate_xfer_zombie")) {
+                       switch_channel_set_flag(caller_channel, CF_XFER_ZOMBIE);
+                       oglobals.early_ok = 0;
+                       oglobals.ignore_early_media = 1;
+               }
+
                if ((cdr_var = switch_channel_get_variable(caller_channel, "failed_xml_cdr_prefix"))) {
                        char buf[128] = "";
                        switch_snprintf(buf, sizeof(buf), "%s_total", cdr_var);
@@ -3624,7 +3630,15 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_originate(switch_core_session_t *sess
                        }
 
                        if (caller_channel) {
-                               if (switch_channel_test_flag(peer_channel, CF_ANSWERED)) {
+
+                               if (switch_channel_test_flag(caller_channel, CF_XFER_ZOMBIE) && !switch_channel_up(caller_channel)) {
+                                       if (switch_channel_media_up(peer_channel)) {
+                                               oglobals.idx = IDX_XFER;
+                                               reason = force_reason = SWITCH_CAUSE_ATTENDED_TRANSFER;
+                                               switch_channel_execute_on(peer_channel, "execute_on_orphaned_bleg");
+                                               switch_channel_api_on(peer_channel, "api_on_orphaned_bleg");
+                                       }
+                               } else if (switch_channel_test_flag(peer_channel, CF_ANSWERED)) {
                                        switch_channel_pass_callee_id(peer_channel, caller_channel);
                                        if (switch_channel_test_flag(caller_channel, CF_PROXY_MODE)) {
                                                status = SWITCH_STATUS_SUCCESS;