| File: | src/mod/endpoints/mod_skinny/skinny_server.c |
| Location: | line 2508, column 3 |
| Description: | Assigned value is garbage or undefined |
| 1 | /* | |||
| 2 | * FreeSWITCH Modular Media Switching Software Library / Soft-Switch Application | |||
| 3 | * Copyright (C) 2010, Mathieu Parent <math.parent@gmail.com> | |||
| 4 | * | |||
| 5 | * Version: MPL 1.1 | |||
| 6 | * | |||
| 7 | * The contents of this file are subject to the Mozilla Public License Version | |||
| 8 | * 1.1 (the "License"); you may not use this file except in compliance with | |||
| 9 | * the License. You may obtain a copy of the License at | |||
| 10 | * http://www.mozilla.org/MPL/ | |||
| 11 | * | |||
| 12 | * Software distributed under the License is distributed on an "AS IS" basis, | |||
| 13 | * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License | |||
| 14 | * for the specific language governing rights and limitations under the | |||
| 15 | * License. | |||
| 16 | * | |||
| 17 | * The Original Code is FreeSWITCH Modular Media Switching Software Library / Soft-Switch Application | |||
| 18 | * | |||
| 19 | * The Initial Developer of the Original Code is | |||
| 20 | * Mathieu Parent <math.parent@gmail.com> | |||
| 21 | * Portions created by the Initial Developer are Copyright (C) | |||
| 22 | * the Initial Developer. All Rights Reserved. | |||
| 23 | * | |||
| 24 | * Contributor(s): | |||
| 25 | * | |||
| 26 | * Mathieu Parent <math.parent@gmail.com> | |||
| 27 | * | |||
| 28 | * | |||
| 29 | * skinny_server.c -- Skinny Call Control Protocol (SCCP) Endpoint Module | |||
| 30 | * | |||
| 31 | */ | |||
| 32 | #include <switch.h> | |||
| 33 | #include "mod_skinny.h" | |||
| 34 | #include "skinny_protocol.h" | |||
| 35 | #include "skinny_tables.h" | |||
| 36 | #include "skinny_server.h" | |||
| 37 | ||||
| 38 | uint32_t soft_key_template_default_textids[] = { | |||
| 39 | SKINNY_TEXTID_REDIAL, | |||
| 40 | SKINNY_TEXTID_NEWCALL, | |||
| 41 | SKINNY_TEXTID_HOLD, | |||
| 42 | SKINNY_TEXTID_TRANSFER, | |||
| 43 | SKINNY_TEXTID_CFWDALL, | |||
| 44 | SKINNY_TEXTID_CFWDBUSY, | |||
| 45 | SKINNY_TEXTID_CFWDNOANSWER, | |||
| 46 | SKINNY_TEXTID_BACKSPACE, | |||
| 47 | SKINNY_TEXTID_ENDCALL, | |||
| 48 | SKINNY_TEXTID_RESUME, | |||
| 49 | SKINNY_TEXTID_ANSWER, | |||
| 50 | SKINNY_TEXTID_INFO, | |||
| 51 | SKINNY_TEXTID_CONF, | |||
| 52 | SKINNY_TEXTID_PARK, | |||
| 53 | SKINNY_TEXTID_JOIN, | |||
| 54 | SKINNY_TEXTID_MEETME, | |||
| 55 | SKINNY_TEXTID_CALLPICKUP, | |||
| 56 | SKINNY_TEXTID_GRPCALLPICKUP, | |||
| 57 | SKINNY_TEXTID_DND, | |||
| 58 | SKINNY_TEXTID_IDIVERT | |||
| 59 | }; | |||
| 60 | ||||
| 61 | uint32_t soft_key_template_default_events[] = { | |||
| 62 | SOFTKEY_REDIAL, | |||
| 63 | SOFTKEY_NEWCALL, | |||
| 64 | SOFTKEY_HOLD, | |||
| 65 | SOFTKEY_TRANSFER, | |||
| 66 | SOFTKEY_CFWDALL, | |||
| 67 | SOFTKEY_CFWDBUSY, | |||
| 68 | SOFTKEY_CFWDNOANSWER, | |||
| 69 | SOFTKEY_BACKSPACE, | |||
| 70 | SOFTKEY_ENDCALL, | |||
| 71 | SOFTKEY_RESUME, | |||
| 72 | SOFTKEY_ANSWER, | |||
| 73 | SOFTKEY_INFO, | |||
| 74 | SOFTKEY_CONF, | |||
| 75 | SOFTKEY_PARK, | |||
| 76 | SOFTKEY_JOIN, | |||
| 77 | SOFTKEY_MEETME, | |||
| 78 | SOFTKEY_CALLPICKUP, | |||
| 79 | SOFTKEY_GRPCALLPICKUP, | |||
| 80 | SOFTKEY_DND, | |||
| 81 | SOFTKEY_IDIVERT | |||
| 82 | }; | |||
| 83 | ||||
| 84 | /*****************************************************************************/ | |||
| 85 | /* SESSION FUNCTIONS */ | |||
| 86 | /*****************************************************************************/ | |||
| 87 | switch_status_t skinny_create_incoming_session(listener_t *listener, uint32_t *line_instance_p, switch_core_session_t **session) | |||
| 88 | { | |||
| 89 | uint32_t line_instance; | |||
| 90 | switch_core_session_t *nsession; | |||
| 91 | switch_channel_t *channel; | |||
| 92 | private_t *tech_pvt; | |||
| 93 | char name[128]; | |||
| 94 | char *sql; | |||
| 95 | struct line_stat_res_message *button = NULL((void*)0); | |||
| 96 | ||||
| 97 | line_instance = *line_instance_p; | |||
| 98 | if((nsession = skinny_profile_find_session(listener->profile, listener, line_instance_p, 0))) { | |||
| 99 | if(skinny_line_get_state(listener, *line_instance_p, 0) == SKINNY_OFF_HOOK) { | |||
| 100 | /* Reuse existing session */ | |||
| 101 | *session = nsession; | |||
| 102 | return SWITCH_STATUS_SUCCESS; | |||
| 103 | } | |||
| 104 | switch_core_session_rwunlock(nsession); | |||
| 105 | } | |||
| 106 | *line_instance_p = line_instance; | |||
| 107 | if(*line_instance_p == 0) { | |||
| 108 | *line_instance_p = 1; | |||
| 109 | } | |||
| 110 | ||||
| 111 | skinny_hold_active_calls(listener); | |||
| 112 | ||||
| 113 | skinny_line_get(listener, *line_instance_p, &button); | |||
| 114 | ||||
| 115 | if (!button || !button->shortname[0]) { | |||
| 116 | skinny_log_l(listener, SWITCH_LOG_CRIT, "Line %d not found on device\n", *line_instance_p)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 116, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Line %d not found on device\n", (_zstr(listener->device_name ) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port, *line_instance_p); | |||
| 117 | goto error; | |||
| 118 | } | |||
| 119 | ||||
| 120 | if (!(nsession = switch_core_session_request(skinny_get_endpoint_interface(),switch_core_session_request_uuid(skinny_get_endpoint_interface (), SWITCH_CALL_DIRECTION_INBOUND, SOF_NONE, ((void*)0), ((void *)0)) | |||
| 121 | SWITCH_CALL_DIRECTION_INBOUND, SOF_NONE, NULL)switch_core_session_request_uuid(skinny_get_endpoint_interface (), SWITCH_CALL_DIRECTION_INBOUND, SOF_NONE, ((void*)0), ((void *)0)))) { | |||
| 122 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Error Creating Session\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 122, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Error Creating Session\n", (_zstr(listener->device_name) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port); | |||
| 123 | goto error; | |||
| 124 | } | |||
| 125 | ||||
| 126 | if (!(tech_pvt = (struct private_object *) switch_core_session_alloc(nsession, sizeof(*tech_pvt))switch_core_perform_session_alloc(nsession, sizeof(*tech_pvt) , "skinny_server.c", (const char *)__func__, 126))) { | |||
| 127 | skinny_log_ls_msg(listener, nsession, SWITCH_LOG_CRIT, "Error Creating Session private object\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 127, (const char*)(nsession), SWITCH_LOG_CRIT , "[%s:%d @ %s:%d] " "Error Creating Session private object\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 128 | goto error; | |||
| 129 | } | |||
| 130 | ||||
| 131 | switch_core_session_add_stream(nsession, NULL((void*)0)); | |||
| 132 | ||||
| 133 | tech_init(tech_pvt, listener->profile, nsession); | |||
| 134 | ||||
| 135 | channel = switch_core_session_get_channel(nsession); | |||
| 136 | ||||
| 137 | snprintf(name, sizeof(name), "SKINNY/%s/%s:%d/%d", listener->profile->name, | |||
| 138 | listener->device_name, listener->device_instance, *line_instance_p); | |||
| 139 | switch_channel_set_name(channel, name); | |||
| 140 | ||||
| 141 | if (switch_core_session_thread_launch(nsession) != SWITCH_STATUS_SUCCESS) { | |||
| 142 | skinny_log_ls_msg(listener, nsession, SWITCH_LOG_CRIT, "Error Creating Session thread\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 142, (const char*)(nsession), SWITCH_LOG_CRIT , "[%s:%d @ %s:%d] " "Error Creating Session thread\n", (_zstr (listener->device_name) ? "_undef_" : listener->device_name ), listener->device_instance, (_zstr(listener->remote_ip ) ? "_undef_" : listener->remote_ip), listener->remote_port ); | |||
| 143 | goto error; | |||
| 144 | } | |||
| 145 | if (switch_core_session_read_lock(nsession) != SWITCH_STATUS_SUCCESS) { | |||
| 146 | skinny_log_ls_msg(listener, nsession, SWITCH_LOG_CRIT, "Error Locking Session\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 146, (const char*)(nsession), SWITCH_LOG_CRIT , "[%s:%d @ %s:%d] " "Error Locking Session\n", (_zstr(listener ->device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port); | |||
| 147 | goto error; | |||
| 148 | } | |||
| 149 | /* First create the caller profile in the patterns Dialplan */ | |||
| 150 | if (!(tech_pvt->caller_profile = switch_caller_profile_new(switch_core_session_get_pool(nsession), | |||
| 151 | NULL((void*)0), listener->profile->patterns_dialplan, | |||
| 152 | button->displayname, button->shortname, | |||
| 153 | listener->remote_ip, NULL((void*)0), NULL((void*)0), NULL((void*)0), | |||
| 154 | "skinny" /* modname */, | |||
| 155 | listener->profile->patterns_context, | |||
| 156 | "")) != 0) { | |||
| 157 | skinny_log_ls_msg(listener, nsession, SWITCH_LOG_CRIT, "Error Creating Session caller profile\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 157, (const char*)(nsession), SWITCH_LOG_CRIT , "[%s:%d @ %s:%d] " "Error Creating Session caller profile\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 158 | goto error; | |||
| 159 | } | |||
| 160 | ||||
| 161 | switch_channel_set_caller_profile(channel, tech_pvt->caller_profile); | |||
| 162 | ||||
| 163 | if ((sql = switch_mprintf( | |||
| 164 | "INSERT INTO skinny_active_lines " | |||
| 165 | "(device_name, device_instance, line_instance, channel_uuid, call_id, call_state) " | |||
| 166 | "SELECT device_name, device_instance, line_instance, '%q', %d, %d " | |||
| 167 | "FROM skinny_lines " | |||
| 168 | "WHERE value='%q'", | |||
| 169 | switch_core_session_get_uuid(nsession), tech_pvt->call_id, SKINNY_ON_HOOK, button->shortname | |||
| 170 | ))) { | |||
| 171 | skinny_execute_sql(listener->profile, sql, listener->profile->sql_mutex); | |||
| 172 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 173 | } | |||
| 174 | skinny_session_set_variables(nsession, listener, *line_instance_p); | |||
| 175 | ||||
| 176 | send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, *line_instance_p, tech_pvt->call_id)perform_send_set_ringer(listener, "skinny_server.c", (const char *)__func__, 176, SKINNY_RING_OFF, SKINNY_RING_FOREVER, *line_instance_p , tech_pvt->call_id); | |||
| 177 | send_set_speaker_mode(listener, SKINNY_SPEAKER_ON)perform_send_set_speaker_mode(listener, "skinny_server.c", (const char *)__func__, 177, SKINNY_SPEAKER_ON); | |||
| 178 | send_set_lamp(listener, SKINNY_BUTTON_LINE, *line_instance_p, SKINNY_LAMP_ON)perform_send_set_lamp(listener, "skinny_server.c", (const char *)__func__, 178, SKINNY_BUTTON_LINE, *line_instance_p, SKINNY_LAMP_ON ); | |||
| 179 | skinny_line_set_state(listener, *line_instance_p, tech_pvt->call_id, SKINNY_OFF_HOOK)skinny_line_perform_set_state("skinny_server.c", (const char * )__func__, 179, listener, *line_instance_p, tech_pvt->call_id , SKINNY_OFF_HOOK); | |||
| 180 | send_select_soft_keys(listener, *line_instance_p, tech_pvt->call_id, SKINNY_KEY_SET_OFF_HOOK, 0xffff)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 180, *line_instance_p, tech_pvt->call_id , SKINNY_KEY_SET_OFF_HOOK, 0xffff); | |||
| 181 | ||||
| 182 | send_display_prompt_status_textid(listener, 0, SKINNY_TEXTID_ENTER_NUMBER, *line_instance_p, tech_pvt->call_id)perform_send_display_prompt_status_textid(listener, "skinny_server.c" , (const char *)__func__, 182, 0, SKINNY_TEXTID_ENTER_NUMBER, *line_instance_p, tech_pvt->call_id); | |||
| 183 | ||||
| 184 | send_activate_call_plane(listener, *line_instance_p)perform_send_activate_call_plane(listener, "skinny_server.c", (const char *)__func__, 184, *line_instance_p); | |||
| 185 | if (switch_channel_get_state(channel) == CS_NEW) { | |||
| 186 | switch_channel_set_state(channel, CS_HIBERNATE)switch_channel_perform_set_state(channel, "skinny_server.c", ( const char *)__func__, 186, CS_HIBERNATE); | |||
| 187 | } else { | |||
| 188 | skinny_log_ls_msg(listener, nsession, SWITCH_LOG_CRIT,switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 189, (const char*)(nsession), SWITCH_LOG_CRIT , "[%s:%d @ %s:%d] " "Wow! this channel should be in CS_NEW state, but it is not!\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port) | |||
| 189 | "Wow! this channel should be in CS_NEW state, but it is not!\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 189, (const char*)(nsession), SWITCH_LOG_CRIT , "[%s:%d @ %s:%d] " "Wow! this channel should be in CS_NEW state, but it is not!\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 190 | } | |||
| 191 | ||||
| 192 | goto done; | |||
| 193 | error: | |||
| 194 | skinny_log_l(listener, SWITCH_LOG_CRIT, "Failed to create incoming session for line instance %d", *line_instance_p)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 194, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Failed to create incoming session for line instance %d", (_zstr (listener->device_name) ? "_undef_" : listener->device_name ), listener->device_instance, (_zstr(listener->remote_ip ) ? "_undef_" : listener->remote_ip), listener->remote_port , *line_instance_p); | |||
| 195 | if (nsession) { | |||
| 196 | switch_core_session_destroy(&nsession)switch_core_session_perform_destroy(&nsession, "skinny_server.c" , (const char *)__func__, 196); | |||
| 197 | } | |||
| 198 | ||||
| 199 | listener->profile->ib_failed_calls++; | |||
| 200 | return SWITCH_STATUS_FALSE; | |||
| 201 | ||||
| 202 | done: | |||
| 203 | *session = nsession; | |||
| 204 | listener->profile->ib_calls++; | |||
| 205 | return SWITCH_STATUS_SUCCESS; | |||
| 206 | } | |||
| 207 | ||||
| 208 | skinny_action_t skinny_session_dest_match_pattern(switch_core_session_t *session, char **data) | |||
| 209 | { | |||
| 210 | skinny_action_t action = SKINNY_ACTION_DROP; | |||
| 211 | switch_channel_t *channel = NULL((void*)0); | |||
| 212 | private_t *tech_pvt = NULL((void*)0); | |||
| 213 | ||||
| 214 | switch_assert(session)((session) ? (void) (0) : __assert_fail ("session", "skinny_server.c" , 214, __PRETTY_FUNCTION__)); | |||
| 215 | ||||
| 216 | channel = switch_core_session_get_channel(session); | |||
| 217 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 218 | ||||
| 219 | /* this part of the code is similar to switch_core_standard_on_routing() */ | |||
| 220 | if (!zstr(tech_pvt->profile->patterns_dialplan)_zstr(tech_pvt->profile->patterns_dialplan)) { | |||
| 221 | switch_dialplan_interface_t *dialplan_interface = NULL((void*)0); | |||
| 222 | switch_caller_extension_t *extension = NULL((void*)0); | |||
| 223 | char *expanded = NULL((void*)0); | |||
| 224 | char *dpstr = NULL((void*)0); | |||
| 225 | char *dp[25]; | |||
| 226 | int argc, x; | |||
| 227 | ||||
| 228 | if ((dpstr = switch_core_session_strdup(session, tech_pvt->profile->patterns_dialplan)switch_core_perform_session_strdup(session, tech_pvt->profile ->patterns_dialplan, "skinny_server.c", (const char *)__func__ , 228))) { | |||
| 229 | expanded = switch_channel_expand_variables(channel, dpstr)switch_channel_expand_variables_check(channel, dpstr, ((void* )0), ((void*)0), 0); | |||
| 230 | argc = switch_separate_string(expanded, ',', dp, (sizeof(dp) / sizeof(dp[0]))); | |||
| 231 | for (x = 0; x < argc; x++) { | |||
| 232 | char *dpname = dp[x]; | |||
| 233 | char *dparg = NULL((void*)0); | |||
| 234 | ||||
| 235 | if (dpname) { | |||
| 236 | if ((dparg = strchr(dpname, ':')(__extension__ (__builtin_constant_p (':') && !__builtin_constant_p (dpname) && (':') == '\0' ? (char *) __rawmemchr (dpname , ':') : __builtin_strchr (dpname, ':'))))) { | |||
| 237 | *dparg++ = '\0'; | |||
| 238 | } | |||
| 239 | } else { | |||
| 240 | continue; | |||
| 241 | } | |||
| 242 | if (!(dialplan_interface = switch_loadable_module_get_dialplan_interface(dpname))) { | |||
| 243 | continue; | |||
| 244 | } | |||
| 245 | ||||
| 246 | extension = dialplan_interface->hunt_function(session, dparg, NULL((void*)0)); | |||
| 247 | UNPROTECT_INTERFACE(dialplan_interface)if (dialplan_interface) {switch_mutex_lock(dialplan_interface ->reflock); switch_thread_rwlock_unlock(dialplan_interface ->rwlock); switch_thread_rwlock_unlock(dialplan_interface-> parent->rwlock); dialplan_interface->refs--; dialplan_interface ->parent->refs--; switch_mutex_unlock(dialplan_interface ->reflock);}; | |||
| 248 | ||||
| 249 | if (extension) { | |||
| 250 | goto found; | |||
| 251 | } | |||
| 252 | } | |||
| 253 | } | |||
| 254 | found: | |||
| 255 | while (extension && extension->current_application) { | |||
| 256 | switch_caller_application_t *current_application = extension->current_application; | |||
| 257 | ||||
| 258 | extension->current_application = extension->current_application->next; | |||
| 259 | ||||
| 260 | if (!strcmp(current_application->application_name, "skinny-route")__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (current_application->application_name) && __builtin_constant_p ("skinny-route") && (__s1_len = __builtin_strlen (current_application ->application_name), __s2_len = __builtin_strlen ("skinny-route" ), (!((size_t)(const void *)((current_application->application_name ) + 1) - (size_t)(const void *)(current_application->application_name ) == 1) || __s1_len >= 4) && (!((size_t)(const void *)(("skinny-route") + 1) - (size_t)(const void *)("skinny-route" ) == 1) || __s2_len >= 4)) ? __builtin_strcmp (current_application ->application_name, "skinny-route") : (__builtin_constant_p (current_application->application_name) && ((size_t )(const void *)((current_application->application_name) + 1 ) - (size_t)(const void *)(current_application->application_name ) == 1) && (__s1_len = __builtin_strlen (current_application ->application_name), __s1_len < 4) ? (__builtin_constant_p ("skinny-route") && ((size_t)(const void *)(("skinny-route" ) + 1) - (size_t)(const void *)("skinny-route") == 1) ? __builtin_strcmp (current_application->application_name, "skinny-route") : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) ("skinny-route"); int __result = (((const unsigned char *) (const char *) (current_application->application_name ))[0] - __s2[0]); if (__s1_len > 0 && __result == 0 ) { __result = (((const unsigned char *) (const char *) (current_application ->application_name))[1] - __s2[1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (current_application->application_name))[2] - __s2 [2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (current_application ->application_name))[3] - __s2[3]); } } __result; }))) : ( __builtin_constant_p ("skinny-route") && ((size_t)(const void *)(("skinny-route") + 1) - (size_t)(const void *)("skinny-route" ) == 1) && (__s2_len = __builtin_strlen ("skinny-route" ), __s2_len < 4) ? (__builtin_constant_p (current_application ->application_name) && ((size_t)(const void *)((current_application ->application_name) + 1) - (size_t)(const void *)(current_application ->application_name) == 1) ? __builtin_strcmp (current_application ->application_name, "skinny-route") : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (current_application->application_name); int __result = (((const unsigned char *) (const char *) ("skinny-route"))[0 ] - __s2[0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) ("skinny-route" ))[1] - __s2[1]); if (__s2_len > 1 && __result == 0 ) { __result = (((const unsigned char *) (const char *) ("skinny-route" ))[2] - __s2[2]); if (__s2_len > 2 && __result == 0 ) __result = (((const unsigned char *) (const char *) ("skinny-route" ))[3] - __s2[3]); } } __result; })))) : __builtin_strcmp (current_application ->application_name, "skinny-route")))); }) || !strcmp(current_application->application_name, "skinny-process")__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (current_application->application_name) && __builtin_constant_p ("skinny-process") && (__s1_len = __builtin_strlen ( current_application->application_name), __s2_len = __builtin_strlen ("skinny-process"), (!((size_t)(const void *)((current_application ->application_name) + 1) - (size_t)(const void *)(current_application ->application_name) == 1) || __s1_len >= 4) && ( !((size_t)(const void *)(("skinny-process") + 1) - (size_t)(const void *)("skinny-process") == 1) || __s2_len >= 4)) ? __builtin_strcmp (current_application->application_name, "skinny-process") : (__builtin_constant_p (current_application->application_name ) && ((size_t)(const void *)((current_application-> application_name) + 1) - (size_t)(const void *)(current_application ->application_name) == 1) && (__s1_len = __builtin_strlen (current_application->application_name), __s1_len < 4) ? (__builtin_constant_p ("skinny-process") && ((size_t )(const void *)(("skinny-process") + 1) - (size_t)(const void *)("skinny-process") == 1) ? __builtin_strcmp (current_application ->application_name, "skinny-process") : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) ("skinny-process"); int __result = (((const unsigned char *) (const char *) (current_application->application_name))[0 ] - __s2[0]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (current_application ->application_name))[1] - __s2[1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (current_application->application_name))[2] - __s2 [2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (current_application ->application_name))[3] - __s2[3]); } } __result; }))) : ( __builtin_constant_p ("skinny-process") && ((size_t)( const void *)(("skinny-process") + 1) - (size_t)(const void * )("skinny-process") == 1) && (__s2_len = __builtin_strlen ("skinny-process"), __s2_len < 4) ? (__builtin_constant_p (current_application->application_name) && ((size_t )(const void *)((current_application->application_name) + 1 ) - (size_t)(const void *)(current_application->application_name ) == 1) ? __builtin_strcmp (current_application->application_name , "skinny-process") : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (current_application ->application_name); int __result = (((const unsigned char *) (const char *) ("skinny-process"))[0] - __s2[0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) ("skinny-process"))[1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) ("skinny-process"))[2] - __s2 [2]); if (__s2_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) ("skinny-process")) [3] - __s2[3]); } } __result; })))) : __builtin_strcmp (current_application ->application_name, "skinny-process")))); })) { | |||
| 261 | action = SKINNY_ACTION_PROCESS; | |||
| 262 | } else if (!strcmp(current_application->application_name, "skinny-drop")__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (current_application->application_name) && __builtin_constant_p ("skinny-drop") && (__s1_len = __builtin_strlen (current_application ->application_name), __s2_len = __builtin_strlen ("skinny-drop" ), (!((size_t)(const void *)((current_application->application_name ) + 1) - (size_t)(const void *)(current_application->application_name ) == 1) || __s1_len >= 4) && (!((size_t)(const void *)(("skinny-drop") + 1) - (size_t)(const void *)("skinny-drop" ) == 1) || __s2_len >= 4)) ? __builtin_strcmp (current_application ->application_name, "skinny-drop") : (__builtin_constant_p (current_application->application_name) && ((size_t )(const void *)((current_application->application_name) + 1 ) - (size_t)(const void *)(current_application->application_name ) == 1) && (__s1_len = __builtin_strlen (current_application ->application_name), __s1_len < 4) ? (__builtin_constant_p ("skinny-drop") && ((size_t)(const void *)(("skinny-drop" ) + 1) - (size_t)(const void *)("skinny-drop") == 1) ? __builtin_strcmp (current_application->application_name, "skinny-drop") : ( __extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) ("skinny-drop"); int __result = (((const unsigned char *) (const char *) (current_application->application_name ))[0] - __s2[0]); if (__s1_len > 0 && __result == 0 ) { __result = (((const unsigned char *) (const char *) (current_application ->application_name))[1] - __s2[1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (current_application->application_name))[2] - __s2 [2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (current_application ->application_name))[3] - __s2[3]); } } __result; }))) : ( __builtin_constant_p ("skinny-drop") && ((size_t)(const void *)(("skinny-drop") + 1) - (size_t)(const void *)("skinny-drop" ) == 1) && (__s2_len = __builtin_strlen ("skinny-drop" ), __s2_len < 4) ? (__builtin_constant_p (current_application ->application_name) && ((size_t)(const void *)((current_application ->application_name) + 1) - (size_t)(const void *)(current_application ->application_name) == 1) ? __builtin_strcmp (current_application ->application_name, "skinny-drop") : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (current_application->application_name); int __result = ( ((const unsigned char *) (const char *) ("skinny-drop"))[0] - __s2[0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) ("skinny-drop"))[ 1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) ("skinny-drop" ))[2] - __s2[2]); if (__s2_len > 2 && __result == 0 ) __result = (((const unsigned char *) (const char *) ("skinny-drop" ))[3] - __s2[3]); } } __result; })))) : __builtin_strcmp (current_application ->application_name, "skinny-drop")))); })) { | |||
| 263 | action = SKINNY_ACTION_DROP; | |||
| 264 | } else if (!strcmp(current_application->application_name, "skinny-wait")__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (current_application->application_name) && __builtin_constant_p ("skinny-wait") && (__s1_len = __builtin_strlen (current_application ->application_name), __s2_len = __builtin_strlen ("skinny-wait" ), (!((size_t)(const void *)((current_application->application_name ) + 1) - (size_t)(const void *)(current_application->application_name ) == 1) || __s1_len >= 4) && (!((size_t)(const void *)(("skinny-wait") + 1) - (size_t)(const void *)("skinny-wait" ) == 1) || __s2_len >= 4)) ? __builtin_strcmp (current_application ->application_name, "skinny-wait") : (__builtin_constant_p (current_application->application_name) && ((size_t )(const void *)((current_application->application_name) + 1 ) - (size_t)(const void *)(current_application->application_name ) == 1) && (__s1_len = __builtin_strlen (current_application ->application_name), __s1_len < 4) ? (__builtin_constant_p ("skinny-wait") && ((size_t)(const void *)(("skinny-wait" ) + 1) - (size_t)(const void *)("skinny-wait") == 1) ? __builtin_strcmp (current_application->application_name, "skinny-wait") : ( __extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) ("skinny-wait"); int __result = (((const unsigned char *) (const char *) (current_application->application_name ))[0] - __s2[0]); if (__s1_len > 0 && __result == 0 ) { __result = (((const unsigned char *) (const char *) (current_application ->application_name))[1] - __s2[1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (current_application->application_name))[2] - __s2 [2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (current_application ->application_name))[3] - __s2[3]); } } __result; }))) : ( __builtin_constant_p ("skinny-wait") && ((size_t)(const void *)(("skinny-wait") + 1) - (size_t)(const void *)("skinny-wait" ) == 1) && (__s2_len = __builtin_strlen ("skinny-wait" ), __s2_len < 4) ? (__builtin_constant_p (current_application ->application_name) && ((size_t)(const void *)((current_application ->application_name) + 1) - (size_t)(const void *)(current_application ->application_name) == 1) ? __builtin_strcmp (current_application ->application_name, "skinny-wait") : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (current_application->application_name); int __result = ( ((const unsigned char *) (const char *) ("skinny-wait"))[0] - __s2[0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) ("skinny-wait"))[ 1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) ("skinny-wait" ))[2] - __s2[2]); if (__s2_len > 2 && __result == 0 ) __result = (((const unsigned char *) (const char *) ("skinny-wait" ))[3] - __s2[3]); } } __result; })))) : __builtin_strcmp (current_application ->application_name, "skinny-wait")))); })) { | |||
| 265 | action = SKINNY_ACTION_WAIT; | |||
| 266 | *data = switch_core_session_strdup(session, current_application->application_data)switch_core_perform_session_strdup(session, current_application ->application_data, "skinny_server.c", (const char *)__func__ , 266); | |||
| 267 | } else { | |||
| 268 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 268, (const char*)(session), SWITCH_LOG_WARNING, | |||
| 269 | "Unknown skinny dialplan application %s\n", current_application->application_name); | |||
| 270 | } | |||
| 271 | } | |||
| 272 | } | |||
| 273 | return action; | |||
| 274 | } | |||
| 275 | ||||
| 276 | ||||
| 277 | switch_status_t skinny_session_process_dest(switch_core_session_t *session, listener_t *listener, uint32_t line_instance, char *dest, char append_dest, uint32_t backspace) | |||
| 278 | { | |||
| 279 | switch_channel_t *channel = NULL((void*)0); | |||
| 280 | private_t *tech_pvt = NULL((void*)0); | |||
| 281 | ||||
| 282 | switch_assert(session)((session) ? (void) (0) : __assert_fail ("session", "skinny_server.c" , 282, __PRETTY_FUNCTION__)); | |||
| 283 | switch_assert(listener)((listener) ? (void) (0) : __assert_fail ("listener", "skinny_server.c" , 283, __PRETTY_FUNCTION__)); | |||
| 284 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 284, __PRETTY_FUNCTION__)); | |||
| 285 | ||||
| 286 | channel = switch_core_session_get_channel(session); | |||
| 287 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 288 | ||||
| 289 | // get listener profile setting for ringdown/autodial | |||
| 290 | // if initial offhook - and we have a ringdown/autodial configured, just dial it in one shot | |||
| 291 | if (!dest && append_dest == '\0' && listener->ext_autodial ) { | |||
| 292 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 292, (const char*)(session), SWITCH_LOG_WARNING, | |||
| 293 | "triggering auto dial to (%s)\n", listener->ext_autodial); | |||
| 294 | ||||
| 295 | tech_pvt->caller_profile->destination_number = switch_core_strdup(tech_pvt->caller_profile->pool, listener->ext_autodial)switch_core_perform_strdup(tech_pvt->caller_profile->pool , listener->ext_autodial, "skinny_server.c", (const char * )__func__, 295); | |||
| 296 | switch_set_flag_locked(tech_pvt, TFLAG_FORCE_ROUTE)((tech_pvt->flag_mutex != ((void*)0)) ? (void) (0) : __assert_fail ("tech_pvt->flag_mutex != ((void*)0)", "skinny_server.c", 296, __PRETTY_FUNCTION__));switch_mutex_lock(tech_pvt->flag_mutex );(tech_pvt)->flags |= (TFLAG_FORCE_ROUTE);switch_mutex_unlock (tech_pvt->flag_mutex);; | |||
| 297 | } else if (!dest) { | |||
| 298 | if (strlen(tech_pvt->caller_profile->destination_number) == 0) {/* no digit yet */ | |||
| 299 | send_start_tone(listener, SKINNY_TONE_DIALTONE, 0, line_instance, tech_pvt->call_id)perform_send_start_tone(listener, "skinny_server.c", (const char *)__func__, 299, SKINNY_TONE_DIALTONE, 0, line_instance, tech_pvt ->call_id); | |||
| 300 | } | |||
| 301 | if (backspace && strlen(tech_pvt->caller_profile->destination_number)) { /* backspace */ | |||
| 302 | tech_pvt->caller_profile->destination_number[strlen(tech_pvt->caller_profile->destination_number)-1] = '\0'; | |||
| 303 | if (strlen(tech_pvt->caller_profile->destination_number) == 0) { | |||
| 304 | send_select_soft_keys(listener, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_OFF_HOOK, 0xffff)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 304, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_OFF_HOOK , 0xffff); | |||
| 305 | } | |||
| 306 | send_back_space_request(listener, line_instance, tech_pvt->call_id)perform_send_back_space_request(listener, "skinny_server.c", ( const char *)__func__, 306, line_instance, tech_pvt->call_id ); | |||
| 307 | } | |||
| 308 | if (append_dest != '\0') {/* append digit */ | |||
| 309 | tech_pvt->caller_profile->destination_number = switch_core_sprintf(tech_pvt->caller_profile->pool, | |||
| 310 | "%s%c", tech_pvt->caller_profile->destination_number, append_dest); | |||
| 311 | } | |||
| 312 | if (strlen(tech_pvt->caller_profile->destination_number) == 1) {/* first digit */ | |||
| 313 | if(!backspace) { | |||
| 314 | send_stop_tone(listener, line_instance, tech_pvt->call_id)perform_send_stop_tone(listener, "skinny_server.c", (const char *)__func__, 314, line_instance, tech_pvt->call_id); | |||
| 315 | } | |||
| 316 | send_select_soft_keys(listener, line_instance, tech_pvt->call_id,perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 317, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_DIGITS_AFTER_DIALING_FIRST_DIGIT , 0xffff) | |||
| 317 | SKINNY_KEY_SET_DIGITS_AFTER_DIALING_FIRST_DIGIT, 0xffff)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 317, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_DIGITS_AFTER_DIALING_FIRST_DIGIT , 0xffff); | |||
| 318 | } | |||
| 319 | } else { | |||
| 320 | tech_pvt->caller_profile->destination_number = switch_core_strdup(tech_pvt->caller_profile->pool, dest)switch_core_perform_strdup(tech_pvt->caller_profile->pool , dest, "skinny_server.c", (const char *)__func__, 320); | |||
| 321 | switch_set_flag_locked(tech_pvt, TFLAG_FORCE_ROUTE)((tech_pvt->flag_mutex != ((void*)0)) ? (void) (0) : __assert_fail ("tech_pvt->flag_mutex != ((void*)0)", "skinny_server.c", 321, __PRETTY_FUNCTION__));switch_mutex_lock(tech_pvt->flag_mutex );(tech_pvt)->flags |= (TFLAG_FORCE_ROUTE);switch_mutex_unlock (tech_pvt->flag_mutex);; | |||
| 322 | } | |||
| 323 | ||||
| 324 | switch_channel_set_state(channel, CS_ROUTING)switch_channel_perform_set_state(channel, "skinny_server.c", ( const char *)__func__, 324, CS_ROUTING); | |||
| 325 | ||||
| 326 | return SWITCH_STATUS_SUCCESS; | |||
| 327 | } | |||
| 328 | ||||
| 329 | switch_status_t skinny_session_send_call_info(switch_core_session_t *session, listener_t *listener, uint32_t line_instance) | |||
| 330 | { | |||
| 331 | private_t *tech_pvt; | |||
| 332 | switch_channel_t *channel; | |||
| 333 | ||||
| 334 | const char *caller_party_name; | |||
| 335 | const char *caller_party_number; | |||
| 336 | const char *called_party_name; | |||
| 337 | const char *called_party_number; | |||
| 338 | uint32_t call_type = 0; | |||
| 339 | ||||
| 340 | channel = switch_core_session_get_channel(session); | |||
| 341 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 342 | ||||
| 343 | switch_assert(tech_pvt->caller_profile != NULL)((tech_pvt->caller_profile != ((void*)0)) ? (void) (0) : __assert_fail ("tech_pvt->caller_profile != ((void*)0)", "skinny_server.c" , 343, __PRETTY_FUNCTION__)); | |||
| 344 | ||||
| 345 | /* Calling party */ | |||
| 346 | if (zstr((caller_party_name = switch_channel_get_variable(channel, "effective_caller_id_name")))_zstr((caller_party_name = switch_channel_get_variable_dup(channel , "effective_caller_id_name", SWITCH_TRUE, -1))) && | |||
| 347 | zstr((caller_party_name = switch_channel_get_variable(channel, "caller_id_name")))_zstr((caller_party_name = switch_channel_get_variable_dup(channel , "caller_id_name", SWITCH_TRUE, -1))) && | |||
| 348 | zstr((caller_party_name = switch_channel_get_variable_partner(channel, "effective_caller_id_name")))_zstr((caller_party_name = switch_channel_get_variable_partner (channel, "effective_caller_id_name"))) && | |||
| 349 | zstr((caller_party_name = switch_channel_get_variable_partner(channel, "caller_id_name")))_zstr((caller_party_name = switch_channel_get_variable_partner (channel, "caller_id_name")))) { | |||
| 350 | caller_party_name = SWITCH_DEFAULT_CLID_NAME""; | |||
| 351 | } | |||
| 352 | if (zstr((caller_party_number = switch_channel_get_variable(channel, "effective_caller_id_number")))_zstr((caller_party_number = switch_channel_get_variable_dup( channel, "effective_caller_id_number", SWITCH_TRUE, -1))) && | |||
| 353 | zstr((caller_party_number = switch_channel_get_variable(channel, "caller_id_number")))_zstr((caller_party_number = switch_channel_get_variable_dup( channel, "caller_id_number", SWITCH_TRUE, -1))) && | |||
| 354 | zstr((caller_party_number = switch_channel_get_variable_partner(channel, "effective_caller_id_number")))_zstr((caller_party_number = switch_channel_get_variable_partner (channel, "effective_caller_id_number"))) && | |||
| 355 | zstr((caller_party_number = switch_channel_get_variable_partner(channel, "caller_id_number")))_zstr((caller_party_number = switch_channel_get_variable_partner (channel, "caller_id_number")))) { | |||
| 356 | caller_party_number = SWITCH_DEFAULT_CLID_NUMBER"0000000000"; | |||
| 357 | } | |||
| 358 | /* Called party */ | |||
| 359 | if (zstr((called_party_name = switch_channel_get_variable(channel, "effective_callee_id_name")))_zstr((called_party_name = switch_channel_get_variable_dup(channel , "effective_callee_id_name", SWITCH_TRUE, -1))) && | |||
| 360 | zstr((called_party_name = switch_channel_get_variable(channel, "callee_id_name")))_zstr((called_party_name = switch_channel_get_variable_dup(channel , "callee_id_name", SWITCH_TRUE, -1))) && | |||
| 361 | zstr((called_party_name = switch_channel_get_variable_partner(channel, "effective_callee_id_name")))_zstr((called_party_name = switch_channel_get_variable_partner (channel, "effective_callee_id_name"))) && | |||
| 362 | zstr((called_party_name = switch_channel_get_variable_partner(channel, "callee_id_name")))_zstr((called_party_name = switch_channel_get_variable_partner (channel, "callee_id_name")))) { | |||
| 363 | called_party_name = SWITCH_DEFAULT_CLID_NAME""; | |||
| 364 | } | |||
| 365 | if (zstr((called_party_number = switch_channel_get_variable(channel, "effective_callee_id_number")))_zstr((called_party_number = switch_channel_get_variable_dup( channel, "effective_callee_id_number", SWITCH_TRUE, -1))) && | |||
| 366 | zstr((called_party_number = switch_channel_get_variable(channel, "callee_id_number")))_zstr((called_party_number = switch_channel_get_variable_dup( channel, "callee_id_number", SWITCH_TRUE, -1))) && | |||
| 367 | zstr((called_party_number = switch_channel_get_variable_partner(channel, "effective_callee_id_number")))_zstr((called_party_number = switch_channel_get_variable_partner (channel, "effective_callee_id_number"))) && | |||
| 368 | zstr((called_party_number = switch_channel_get_variable_partner(channel, "callee_id_number")))_zstr((called_party_number = switch_channel_get_variable_partner (channel, "callee_id_number"))) && | |||
| 369 | zstr((called_party_number = switch_channel_get_variable(channel, "destination_number")))_zstr((called_party_number = switch_channel_get_variable_dup( channel, "destination_number", SWITCH_TRUE, -1)))) { | |||
| 370 | called_party_number = SWITCH_DEFAULT_CLID_NUMBER"0000000000"; | |||
| 371 | } | |||
| 372 | if (switch_channel_direction(channel) == SWITCH_CALL_DIRECTION_OUTBOUND) { | |||
| 373 | call_type = SKINNY_INBOUND_CALL; | |||
| 374 | } else { | |||
| 375 | call_type = SKINNY_OUTBOUND_CALL; | |||
| 376 | } | |||
| 377 | send_call_info(listener,perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 378 | caller_party_name, /* char calling_party_name[40], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 379 | caller_party_number, /* char calling_party[24], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 380 | called_party_name, /* char called_party_name[40], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 381 | called_party_number, /* char called_party[24], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 382 | line_instance, /* uint32_t line_instance, */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 383 | tech_pvt->call_id, /* uint32_t call_id, */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 384 | call_type, /* uint32_t call_type, */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 385 | "", /* TODO char original_called_party_name[40], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 386 | "", /* TODO char original_called_party[24], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 387 | "", /* TODO char last_redirecting_party_name[40], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 388 | "", /* TODO char last_redirecting_party[24], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 389 | 0, /* TODO uint32_t original_called_party_redirect_reason, */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 390 | 0, /* TODO uint32_t last_redirecting_reason, */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 391 | "", /* TODO char calling_party_voice_mailbox[24], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 392 | "", /* TODO char called_party_voice_mailbox[24], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 393 | "", /* TODO char original_called_party_voice_mailbox[24], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 394 | "", /* TODO char last_redirecting_voice_mailbox[24], */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 395 | 1, /* uint32_t call_instance, */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 396 | 1, /* uint32_t call_security_status, */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 397 | 0 /* uint32_t party_pi_restriction_bits */perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0) | |||
| 398 | )perform_send_call_info(listener, "skinny_server.c", (const char *)__func__, 398, caller_party_name, caller_party_number, called_party_name , called_party_number, line_instance, tech_pvt->call_id, call_type , "", "", "", "", 0, 0, "", "", "", "", 1, 1, 0); | |||
| 399 | return SWITCH_STATUS_SUCCESS; | |||
| 400 | } | |||
| 401 | ||||
| 402 | struct skinny_session_send_call_info_all_helper { | |||
| 403 | private_t *tech_pvt; | |||
| 404 | }; | |||
| 405 | ||||
| 406 | int skinny_session_send_call_info_all_callback(void *pArg, int argc, char **argv, char **columnNames) | |||
| 407 | { | |||
| 408 | char *device_name = argv[0]; | |||
| 409 | uint32_t device_instance = atoi(argv[1]); | |||
| 410 | /* uint32_t position = atoi(argv[2]); */ | |||
| 411 | uint32_t line_instance = atoi(argv[3]); | |||
| 412 | /* char *label = argv[4]; */ | |||
| 413 | /* char *value = argv[5]; */ | |||
| 414 | /* char *caller_name = argv[6]; */ | |||
| 415 | /* uint32_t ring_on_idle = atoi(argv[7]); */ | |||
| 416 | /* uint32_t ring_on_active = atoi(argv[8]); */ | |||
| 417 | /* uint32_t busy_trigger = atoi(argv[9]); */ | |||
| 418 | /* char *forward_all = argv[10]; */ | |||
| 419 | /* char *forward_busy = argv[11]; */ | |||
| 420 | /* char *forward_noanswer = argv[12]; */ | |||
| 421 | /* uint32_t noanswer_duration = atoi(argv[13]); */ | |||
| 422 | /* char *channel_uuid = argv[14]; */ | |||
| 423 | /* uint32_t call_id = atoi(argv[15]); */ | |||
| 424 | /* uint32_t call_state = atoi(argv[16]); */ | |||
| 425 | ||||
| 426 | struct skinny_session_send_call_info_all_helper *helper = pArg; | |||
| 427 | listener_t *listener = NULL((void*)0); | |||
| 428 | ||||
| 429 | skinny_profile_find_listener_by_device_name_and_instance(helper->tech_pvt->profile, | |||
| 430 | device_name, device_instance, &listener); | |||
| 431 | if(listener) { | |||
| 432 | skinny_session_send_call_info(helper->tech_pvt->session, listener, line_instance); | |||
| 433 | } | |||
| 434 | return 0; | |||
| 435 | } | |||
| 436 | ||||
| 437 | switch_status_t skinny_session_send_call_info_all(switch_core_session_t *session) | |||
| 438 | { | |||
| 439 | struct skinny_session_send_call_info_all_helper helper = {0}; | |||
| 440 | private_t *tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 441 | ||||
| 442 | helper.tech_pvt = tech_pvt; | |||
| 443 | return skinny_session_walk_lines(tech_pvt->profile, | |||
| 444 | switch_core_session_get_uuid(tech_pvt->session), skinny_session_send_call_info_all_callback, &helper); | |||
| 445 | } | |||
| 446 | ||||
| 447 | struct skinny_session_set_variables_helper { | |||
| 448 | private_t *tech_pvt; | |||
| 449 | switch_channel_t *channel; | |||
| 450 | listener_t *listener; | |||
| 451 | uint32_t count; | |||
| 452 | }; | |||
| 453 | ||||
| 454 | int skinny_session_set_variables_callback(void *pArg, int argc, char **argv, char **columnNames) | |||
| 455 | { | |||
| 456 | char *device_name = argv[0]; | |||
| 457 | uint32_t device_instance = atoi(argv[1]); | |||
| 458 | uint32_t position = atoi(argv[2]); | |||
| 459 | uint32_t line_instance = atoi(argv[3]); | |||
| 460 | char *label = argv[4]; | |||
| 461 | char *value = argv[5]; | |||
| 462 | char *caller_name = argv[6]; | |||
| 463 | /* uint32_t ring_on_idle = atoi(argv[7]); */ | |||
| 464 | /* uint32_t ring_on_active = atoi(argv[8]); */ | |||
| 465 | /* uint32_t busy_trigger = atoi(argv[9]); */ | |||
| 466 | /* char *forward_all = argv[10]; */ | |||
| 467 | /* char *forward_busy = argv[11]; */ | |||
| 468 | /* char *forward_noanswer = argv[12]; */ | |||
| 469 | /* uint32_t noanswer_duration = atoi(argv[13]); */ | |||
| 470 | /* char *channel_uuid = argv[14]; */ | |||
| 471 | /* uint32_t call_id = atoi(argv[15]); */ | |||
| 472 | /* uint32_t call_state = atoi(argv[16]); */ | |||
| 473 | ||||
| 474 | struct skinny_session_set_variables_helper *helper = pArg; | |||
| 475 | char *tmp; | |||
| 476 | listener_t *listener; | |||
| 477 | ||||
| 478 | switch_xml_t xroot, xdomain, xuser, xvariables, xvariable; | |||
| 479 | ||||
| 480 | helper->count++; | |||
| 481 | switch_channel_set_variable_name_printf(helper->channel, device_name, "skinny_device_name_%d", helper->count); | |||
| 482 | if ((tmp = switch_mprintf("%d", device_instance))) { | |||
| 483 | switch_channel_set_variable_name_printf(helper->channel, tmp, "skinny_device_instance_%d", helper->count); | |||
| 484 | switch_safe_free(tmp)if (tmp) {free(tmp);tmp=((void*)0);}; | |||
| 485 | } | |||
| 486 | if ((tmp = switch_mprintf("%d", position))) { | |||
| 487 | switch_channel_set_variable_name_printf(helper->channel, tmp, "skinny_line_position_%d", helper->count); | |||
| 488 | switch_safe_free(tmp)if (tmp) {free(tmp);tmp=((void*)0);}; | |||
| 489 | } | |||
| 490 | if ((tmp = switch_mprintf("%d", line_instance))) { | |||
| 491 | switch_channel_set_variable_name_printf(helper->channel, tmp, "skinny_line_instance_%d", helper->count); | |||
| 492 | switch_safe_free(tmp)if (tmp) {free(tmp);tmp=((void*)0);}; | |||
| 493 | } | |||
| 494 | switch_channel_set_variable_name_printf(helper->channel, label, "skinny_line_label_%d", helper->count); | |||
| 495 | switch_channel_set_variable_name_printf(helper->channel, value, "skinny_line_value_%d", helper->count); | |||
| 496 | switch_channel_set_variable_name_printf(helper->channel, caller_name, "skinny_line_caller_name_%d", helper->count); | |||
| 497 | ||||
| 498 | listener = helper->listener; | |||
| 499 | ||||
| 500 | if ( ! listener ) { | |||
| 501 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(helper->tech_pvt->session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 501, (const char*)(helper->tech_pvt->session), SWITCH_LOG_DEBUG, | |||
| 502 | "no defined listener on channel var setup, will not attempt to set variables\n"); | |||
| 503 | return(0); | |||
| 504 | } | |||
| 505 | ||||
| 506 | /* Process through and extract any variables from the user and set in the channel */ | |||
| 507 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(helper->tech_pvt->session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 507, (const char*)(helper->tech_pvt->session), SWITCH_LOG_DEBUG, | |||
| 508 | "searching for user (id=%s) in profile %s in channel var setup\n", | |||
| 509 | listener->device_name, listener->profile->domain); | |||
| 510 | ||||
| 511 | if (switch_xml_locate_user("id", listener->device_name, listener->profile->domain, "", | |||
| 512 | &xroot, &xdomain, &xuser, NULL((void*)0), NULL((void*)0)) != SWITCH_STATUS_SUCCESS) { | |||
| 513 | ||||
| 514 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(helper->tech_pvt->session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 514, (const char*)(helper->tech_pvt->session), SWITCH_LOG_WARNING, | |||
| 515 | "unable to find user (id=%s) in channel var setup\n", listener->device_name); | |||
| 516 | } | |||
| 517 | ||||
| 518 | if ( xuser ) { | |||
| 519 | char *uid = (char *) switch_xml_attr_soft(xuser, "id"); | |||
| 520 | ||||
| 521 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(helper->tech_pvt->session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 521, (const char*)(helper->tech_pvt->session), SWITCH_LOG_DEBUG, | |||
| 522 | "found user (id=%s) in channel var setup\n", uid); | |||
| 523 | ||||
| 524 | if ((xvariables = switch_xml_child(xuser, "variables"))) { | |||
| 525 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(helper->tech_pvt->session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 525, (const char*)(helper->tech_pvt->session), SWITCH_LOG_DEBUG, | |||
| 526 | "found variables section in user xml"); | |||
| 527 | ||||
| 528 | for (xvariable = switch_xml_child(xvariables, "variable"); xvariable; xvariable = xvariable->next) { | |||
| 529 | char *name = (char *) switch_xml_attr_soft(xvariable, "name"); | |||
| 530 | char *value = (char *) switch_xml_attr_soft(xvariable, "value"); | |||
| 531 | ||||
| 532 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(helper->tech_pvt->session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 532, (const char*)(helper->tech_pvt->session), SWITCH_LOG_DEBUG, | |||
| 533 | "found variable (%s=%s) for user (%s) in channel var setup\n", name, value, listener->device_name); | |||
| 534 | ||||
| 535 | switch_channel_set_variable_name_printf(helper->channel, value, "%s", name); | |||
| 536 | } | |||
| 537 | } | |||
| 538 | } | |||
| 539 | ||||
| 540 | if ( xroot ) { | |||
| 541 | switch_xml_free(xroot); | |||
| 542 | } | |||
| 543 | ||||
| 544 | return 0; | |||
| 545 | } | |||
| 546 | ||||
| 547 | switch_status_t skinny_session_set_variables(switch_core_session_t *session, listener_t *listener, uint32_t line_instance) | |||
| 548 | { | |||
| 549 | switch_status_t status; | |||
| 550 | struct skinny_session_set_variables_helper helper = {0}; | |||
| 551 | ||||
| 552 | helper.tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 553 | helper.channel = switch_core_session_get_channel(session); | |||
| 554 | helper.listener = listener; | |||
| 555 | helper.count = 0; | |||
| 556 | ||||
| 557 | switch_channel_set_variable(helper.channel, "skinny_profile_name", helper.tech_pvt->profile->name)switch_channel_set_variable_var_check(helper.channel, "skinny_profile_name" , helper.tech_pvt->profile->name, SWITCH_TRUE); | |||
| 558 | if (listener) { | |||
| 559 | switch_channel_set_variable(helper.channel, "skinny_device_name", listener->device_name)switch_channel_set_variable_var_check(helper.channel, "skinny_device_name" , listener->device_name, SWITCH_TRUE); | |||
| 560 | switch_channel_set_variable_printf(helper.channel, "skinny_device_instance", "%d", listener->device_instance); | |||
| 561 | switch_channel_set_variable_printf(helper.channel, "skinny_line_instance", "%d", line_instance); | |||
| 562 | } | |||
| 563 | status = skinny_session_walk_lines(helper.tech_pvt->profile, | |||
| 564 | switch_core_session_get_uuid(helper.tech_pvt->session), skinny_session_set_variables_callback, &helper); | |||
| 565 | ||||
| 566 | switch_channel_set_variable_printf(helper.channel, "skinny_lines_count", "%d", helper.count); | |||
| 567 | return status; | |||
| 568 | } | |||
| 569 | ||||
| 570 | struct skinny_ring_lines_helper { | |||
| 571 | private_t *tech_pvt; | |||
| 572 | switch_core_session_t *remote_session; | |||
| 573 | uint32_t lines_count; | |||
| 574 | }; | |||
| 575 | ||||
| 576 | int skinny_ring_lines_callback(void *pArg, int argc, char **argv, char **columnNames) | |||
| 577 | { | |||
| 578 | struct skinny_ring_lines_helper *helper = pArg; | |||
| 579 | char *tmp; | |||
| 580 | char *label; | |||
| 581 | ||||
| 582 | char *device_name = argv[0]; | |||
| 583 | uint32_t device_instance = atoi(argv[1]); | |||
| 584 | /* uint32_t position = atoi(argv[2]); */ | |||
| 585 | uint32_t line_instance = atoi(argv[3]); | |||
| 586 | /* char *label = argv[4]; */ | |||
| 587 | char *value = argv[5]; | |||
| 588 | char *caller_name = argv[6]; | |||
| 589 | uint32_t ring_on_idle = atoi(argv[7]); | |||
| 590 | uint32_t ring_on_active = atoi(argv[8]); | |||
| 591 | /* uint32_t busy_trigger = atoi(argv[9]); */ | |||
| 592 | /* char *forward_all = argv[10]; */ | |||
| 593 | /* char *forward_busy = argv[11]; */ | |||
| 594 | /* char *forward_noanswer = argv[12]; */ | |||
| 595 | /* uint32_t noanswer_duration = atoi(argv[13]); */ | |||
| 596 | /* char *channel_uuid = argv[14]; */ | |||
| 597 | /* uint32_t call_id = atoi(argv[15]); */ | |||
| 598 | /* uint32_t call_state = atoi(argv[16]); */ | |||
| 599 | ||||
| 600 | listener_t *listener = NULL((void*)0); | |||
| 601 | uint32_t active_calls = 0; | |||
| 602 | ||||
| 603 | skinny_profile_find_listener_by_device_name_and_instance(helper->tech_pvt->profile, | |||
| 604 | device_name, device_instance, &listener); | |||
| 605 | if(listener && helper->tech_pvt->session && helper->remote_session) { | |||
| 606 | switch_channel_t *channel = switch_core_session_get_channel(helper->tech_pvt->session); | |||
| 607 | switch_channel_set_state(channel, CS_ROUTING)switch_channel_perform_set_state(channel, "skinny_server.c", ( const char *)__func__, 607, CS_ROUTING); | |||
| 608 | helper->lines_count++; | |||
| 609 | switch_channel_set_variable(channel, "effective_callee_id_number", value)switch_channel_set_variable_var_check(channel, "effective_callee_id_number" , value, SWITCH_TRUE); | |||
| 610 | switch_channel_set_variable(channel, "effective_callee_id_name", caller_name)switch_channel_set_variable_var_check(channel, "effective_callee_id_name" , caller_name, SWITCH_TRUE); | |||
| 611 | ||||
| 612 | active_calls = skinny_line_count_active(listener); | |||
| 613 | ||||
| 614 | skinny_log_l(listener, SWITCH_LOG_DEBUG,switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 616, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Ring Lines Callback with Callee Number (%s), Caller Name (%s), Dest Number (%s), Active Calls (%d)\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, value, caller_name, helper->tech_pvt->caller_profile ->destination_number, active_calls) | |||
| 615 | "Ring Lines Callback with Callee Number (%s), Caller Name (%s), Dest Number (%s), Active Calls (%d)\n",switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 616, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Ring Lines Callback with Callee Number (%s), Caller Name (%s), Dest Number (%s), Active Calls (%d)\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, value, caller_name, helper->tech_pvt->caller_profile ->destination_number, active_calls) | |||
| 616 | value, caller_name, helper->tech_pvt->caller_profile->destination_number, active_calls)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 616, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Ring Lines Callback with Callee Number (%s), Caller Name (%s), Dest Number (%s), Active Calls (%d)\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, value, caller_name, helper->tech_pvt->caller_profile ->destination_number, active_calls); | |||
| 617 | ||||
| 618 | if (helper->remote_session) { | |||
| 619 | switch_core_session_message_t msg = { 0 }; | |||
| 620 | msg.message_id = SWITCH_MESSAGE_INDICATE_DISPLAY; | |||
| 621 | msg.string_array_arg[0] = switch_core_session_strdup(helper->remote_session, caller_name)switch_core_perform_session_strdup(helper->remote_session, caller_name, "skinny_server.c", (const char *)__func__, 621); | |||
| 622 | msg.string_array_arg[1] = switch_core_session_strdup(helper->remote_session, value)switch_core_perform_session_strdup(helper->remote_session, value, "skinny_server.c", (const char *)__func__, 622); | |||
| 623 | msg.from = __FILE__"skinny_server.c"; | |||
| 624 | ||||
| 625 | if (switch_core_session_receive_message(helper->remote_session, &msg)switch_core_session_perform_receive_message(helper->remote_session , &msg, "skinny_server.c", (const char *)__func__, 625) != SWITCH_STATUS_SUCCESS) { | |||
| 626 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(helper->tech_pvt->session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 626, (const char*)(helper->tech_pvt->session), SWITCH_LOG_WARNING, | |||
| 627 | "Unable to send SWITCH_MESSAGE_INDICATE_DISPLAY message to channel %s\n", | |||
| 628 | switch_core_session_get_uuid(helper->remote_session)); | |||
| 629 | } | |||
| 630 | } | |||
| 631 | ||||
| 632 | skinny_line_set_state(listener, line_instance, helper->tech_pvt->call_id, SKINNY_RING_IN)skinny_line_perform_set_state("skinny_server.c", (const char * )__func__, 632, listener, line_instance, helper->tech_pvt-> call_id, SKINNY_RING_IN); | |||
| 633 | send_select_soft_keys(listener, line_instance, helper->tech_pvt->call_id, SKINNY_KEY_SET_RING_IN, 0xffff)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 633, line_instance, helper->tech_pvt-> call_id, SKINNY_KEY_SET_RING_IN, 0xffff); | |||
| 634 | ||||
| 635 | label = skinny_textid2raw(SKINNY_TEXTID_FROM)(SKINNY_TEXTID_FROM > 0 ? switch_mprintf("\200%c", SKINNY_TEXTID_FROM ) : switch_mprintf("")); | |||
| 636 | if ((tmp = switch_mprintf("%s%s", label, helper->tech_pvt->caller_profile->destination_number))) { | |||
| 637 | send_display_prompt_status(listener, 0, tmp, line_instance, helper->tech_pvt->call_id)perform_send_display_prompt_status(listener, "skinny_server.c" , (const char *)__func__, 637, 0, tmp, line_instance, helper-> tech_pvt->call_id); | |||
| 638 | switch_safe_free(tmp)if (tmp) {free(tmp);tmp=((void*)0);}; | |||
| 639 | } | |||
| 640 | switch_safe_free(label)if (label) {free(label);label=((void*)0);}; | |||
| 641 | ||||
| 642 | if ((tmp = switch_mprintf("\005\000\000\000%s", helper->tech_pvt->caller_profile->destination_number))) { | |||
| 643 | send_display_pri_notify(listener, 10 /* message_timeout */, 5 /* priority */, tmp)perform_send_display_pri_notify(listener, "skinny_server.c", ( const char *)__func__, 643, 10 , 5 , tmp); | |||
| 644 | switch_safe_free(tmp)if (tmp) {free(tmp);tmp=((void*)0);}; | |||
| 645 | } | |||
| 646 | skinny_session_send_call_info(helper->tech_pvt->session, listener, line_instance); | |||
| 647 | send_set_lamp(listener, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_BLINK)perform_send_set_lamp(listener, "skinny_server.c", (const char *)__func__, 647, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_BLINK ); | |||
| 648 | ||||
| 649 | if ( active_calls < 1 && ring_on_idle ) { | |||
| 650 | send_set_ringer(listener, SKINNY_RING_INSIDE, SKINNY_RING_FOREVER, line_instance, helper->tech_pvt->call_id)perform_send_set_ringer(listener, "skinny_server.c", (const char *)__func__, 650, SKINNY_RING_INSIDE, SKINNY_RING_FOREVER, line_instance , helper->tech_pvt->call_id); | |||
| 651 | } else if ( active_calls > 0 && ring_on_active ) { | |||
| 652 | send_start_tone(listener, SKINNY_TONE_CALLWAITTONE, 0, line_instance, helper->tech_pvt->call_id)perform_send_start_tone(listener, "skinny_server.c", (const char *)__func__, 652, SKINNY_TONE_CALLWAITTONE, 0, line_instance, helper->tech_pvt->call_id); | |||
| 653 | send_stop_tone(listener, line_instance, helper->tech_pvt->call_id)perform_send_stop_tone(listener, "skinny_server.c", (const char *)__func__, 653, line_instance, helper->tech_pvt->call_id ); | |||
| 654 | } else { | |||
| 655 | send_set_ringer(listener, SKINNY_RING_FLASHONLY, SKINNY_RING_FOREVER, line_instance, helper->tech_pvt->call_id)perform_send_set_ringer(listener, "skinny_server.c", (const char *)__func__, 655, SKINNY_RING_FLASHONLY, SKINNY_RING_FOREVER, line_instance, helper->tech_pvt->call_id); | |||
| 656 | } | |||
| 657 | switch_channel_ring_ready(channel)switch_channel_perform_ring_ready_value(channel, SWITCH_RING_READY_RINGING , "skinny_server.c", (const char *)__func__, 657); | |||
| 658 | } | |||
| 659 | return 0; | |||
| 660 | } | |||
| 661 | ||||
| 662 | switch_call_cause_t skinny_ring_lines(private_t *tech_pvt, switch_core_session_t *remote_session) | |||
| 663 | { | |||
| 664 | switch_status_t status; | |||
| 665 | struct skinny_ring_lines_helper helper = {0}; | |||
| 666 | ||||
| 667 | switch_assert(tech_pvt)((tech_pvt) ? (void) (0) : __assert_fail ("tech_pvt", "skinny_server.c" , 667, __PRETTY_FUNCTION__)); | |||
| 668 | switch_assert(tech_pvt->profile)((tech_pvt->profile) ? (void) (0) : __assert_fail ("tech_pvt->profile" , "skinny_server.c", 668, __PRETTY_FUNCTION__)); | |||
| 669 | switch_assert(tech_pvt->session)((tech_pvt->session) ? (void) (0) : __assert_fail ("tech_pvt->session" , "skinny_server.c", 669, __PRETTY_FUNCTION__)); | |||
| 670 | ||||
| 671 | helper.tech_pvt = tech_pvt; | |||
| 672 | helper.remote_session = remote_session; | |||
| 673 | helper.lines_count = 0; | |||
| 674 | ||||
| 675 | status = skinny_session_walk_lines(tech_pvt->profile, | |||
| 676 | switch_core_session_get_uuid(tech_pvt->session), skinny_ring_lines_callback, &helper); | |||
| 677 | skinny_session_set_variables(tech_pvt->session, NULL((void*)0), 0); | |||
| 678 | ||||
| 679 | if (status != SWITCH_STATUS_SUCCESS) { | |||
| 680 | return SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER; | |||
| 681 | } else if (helper.lines_count == 0) { | |||
| 682 | return SWITCH_CAUSE_UNALLOCATED_NUMBER; | |||
| 683 | } else { | |||
| 684 | return SWITCH_CAUSE_SUCCESS; | |||
| 685 | } | |||
| 686 | } | |||
| 687 | ||||
| 688 | switch_status_t skinny_session_ring_out(switch_core_session_t *session, listener_t *listener, uint32_t line_instance) | |||
| 689 | { | |||
| 690 | private_t *tech_pvt = NULL((void*)0); | |||
| 691 | ||||
| 692 | switch_assert(session)((session) ? (void) (0) : __assert_fail ("session", "skinny_server.c" , 692, __PRETTY_FUNCTION__)); | |||
| 693 | switch_assert(listener)((listener) ? (void) (0) : __assert_fail ("listener", "skinny_server.c" , 693, __PRETTY_FUNCTION__)); | |||
| 694 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 694, __PRETTY_FUNCTION__)); | |||
| 695 | ||||
| 696 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 697 | ||||
| 698 | send_start_tone(listener, SKINNY_TONE_ALERT, 0, line_instance, tech_pvt->call_id)perform_send_start_tone(listener, "skinny_server.c", (const char *)__func__, 698, SKINNY_TONE_ALERT, 0, line_instance, tech_pvt ->call_id); | |||
| 699 | skinny_line_set_state(listener, line_instance, tech_pvt->call_id, SKINNY_RING_OUT)skinny_line_perform_set_state("skinny_server.c", (const char * )__func__, 699, listener, line_instance, tech_pvt->call_id , SKINNY_RING_OUT); | |||
| 700 | send_select_soft_keys(listener, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_RING_OUT, 0xffff)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 700, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_RING_OUT , 0xffff); | |||
| 701 | ||||
| 702 | send_display_prompt_status_textid(listener, 0, SKINNY_TEXTID_RING_OUT, line_instance, tech_pvt->call_id)perform_send_display_prompt_status_textid(listener, "skinny_server.c" , (const char *)__func__, 702, 0, SKINNY_TEXTID_RING_OUT, line_instance , tech_pvt->call_id); | |||
| 703 | ||||
| 704 | skinny_session_send_call_info(session, listener, line_instance); | |||
| 705 | ||||
| 706 | return SWITCH_STATUS_SUCCESS; | |||
| 707 | } | |||
| 708 | ||||
| 709 | ||||
| 710 | struct skinny_session_answer_helper { | |||
| 711 | private_t *tech_pvt; | |||
| 712 | listener_t *listener; | |||
| 713 | uint32_t line_instance; | |||
| 714 | }; | |||
| 715 | ||||
| 716 | int skinny_session_answer_callback(void *pArg, int argc, char **argv, char **columnNames) | |||
| 717 | { | |||
| 718 | struct skinny_session_answer_helper *helper = pArg; | |||
| 719 | listener_t *listener = NULL((void*)0); | |||
| 720 | ||||
| 721 | char *device_name = argv[0]; | |||
| 722 | uint32_t device_instance = atoi(argv[1]); | |||
| 723 | /* uint32_t position = atoi(argv[2]); */ | |||
| 724 | uint32_t line_instance = atoi(argv[3]); | |||
| 725 | /* char *label = argv[4]; */ | |||
| 726 | /* char *value = argv[5]; */ | |||
| 727 | /* char *caller_name = argv[6]; */ | |||
| 728 | /* uint32_t ring_on_idle = atoi(argv[7]); */ | |||
| 729 | /* uint32_t ring_on_active = atoi(argv[8]); */ | |||
| 730 | /* uint32_t busy_trigger = atoi(argv[9]); */ | |||
| 731 | /* char *forward_all = argv[10]; */ | |||
| 732 | /* char *forward_busy = argv[11]; */ | |||
| 733 | /* char *forward_noanswer = argv[12]; */ | |||
| 734 | /* uint32_t noanswer_duration = atoi(argv[13]); */ | |||
| 735 | /* char *channel_uuid = argv[14]; */ | |||
| 736 | /* uint32_t call_id = atoi(argv[15]); */ | |||
| 737 | /* uint32_t call_state = atoi(argv[16]); */ | |||
| 738 | ||||
| 739 | skinny_profile_find_listener_by_device_name_and_instance(helper->tech_pvt->profile, device_name, device_instance, &listener); | |||
| 740 | if(listener) { | |||
| 741 | if(!strcmp(device_name, helper->listener->device_name)__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (device_name) && __builtin_constant_p (helper->listener ->device_name) && (__s1_len = __builtin_strlen (device_name ), __s2_len = __builtin_strlen (helper->listener->device_name ), (!((size_t)(const void *)((device_name) + 1) - (size_t)(const void *)(device_name) == 1) || __s1_len >= 4) && ( !((size_t)(const void *)((helper->listener->device_name ) + 1) - (size_t)(const void *)(helper->listener->device_name ) == 1) || __s2_len >= 4)) ? __builtin_strcmp (device_name , helper->listener->device_name) : (__builtin_constant_p (device_name) && ((size_t)(const void *)((device_name ) + 1) - (size_t)(const void *)(device_name) == 1) && (__s1_len = __builtin_strlen (device_name), __s1_len < 4) ? (__builtin_constant_p (helper->listener->device_name ) && ((size_t)(const void *)((helper->listener-> device_name) + 1) - (size_t)(const void *)(helper->listener ->device_name) == 1) ? __builtin_strcmp (device_name, helper ->listener->device_name) : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (helper-> listener->device_name); int __result = (((const unsigned char *) (const char *) (device_name))[0] - __s2[0]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (device_name))[1] - __s2[1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (device_name))[2] - __s2[2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (device_name))[3] - __s2[3]); } } __result ; }))) : (__builtin_constant_p (helper->listener->device_name ) && ((size_t)(const void *)((helper->listener-> device_name) + 1) - (size_t)(const void *)(helper->listener ->device_name) == 1) && (__s2_len = __builtin_strlen (helper->listener->device_name), __s2_len < 4) ? (__builtin_constant_p (device_name) && ((size_t)(const void *)((device_name ) + 1) - (size_t)(const void *)(device_name) == 1) ? __builtin_strcmp (device_name, helper->listener->device_name) : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (device_name); int __result = (((const unsigned char *) (const char *) (helper->listener->device_name))[0] - __s2[0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (helper->listener ->device_name))[1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (helper->listener->device_name))[2] - __s2[2]) ; if (__s2_len > 2 && __result == 0) __result = (( (const unsigned char *) (const char *) (helper->listener-> device_name))[3] - __s2[3]); } } __result; })))) : __builtin_strcmp (device_name, helper->listener->device_name)))); }) | |||
| 742 | && (device_instance == helper->listener->device_instance) | |||
| 743 | && (line_instance == helper->line_instance)) {/* the answering line */ | |||
| 744 | /* nothing */ | |||
| 745 | skinny_log_l_msg(listener, SWITCH_LOG_DEBUG, "Session Answer Callback - matched helper\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 745, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Session Answer Callback - matched helper\n", (_zstr(listener ->device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port); | |||
| 746 | } else { | |||
| 747 | skinny_log_l_msg(listener, SWITCH_LOG_DEBUG, "Session Answer Callback\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 747, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Session Answer Callback\n", (_zstr(listener->device_name ) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port); | |||
| 748 | ||||
| 749 | send_define_current_time_date(listener)perform_send_define_current_time_date(listener, "skinny_server.c" , (const char *)__func__, 749); | |||
| 750 | send_set_lamp(listener, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_ON)perform_send_set_lamp(listener, "skinny_server.c", (const char *)__func__, 750, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_ON ); | |||
| 751 | skinny_line_set_state(listener, line_instance, helper->tech_pvt->call_id, SKINNY_IN_USE_REMOTELY)skinny_line_perform_set_state("skinny_server.c", (const char * )__func__, 751, listener, line_instance, helper->tech_pvt-> call_id, SKINNY_IN_USE_REMOTELY); | |||
| 752 | send_select_soft_keys(listener, line_instance, helper->tech_pvt->call_id, 10, 0x0002)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 752, line_instance, helper->tech_pvt-> call_id, 10, 0x0002); | |||
| 753 | ||||
| 754 | send_display_prompt_status_textid(listener, 0, SKINNY_TEXTID_IN_USE_REMOTE, line_instance, helper->tech_pvt->call_id)perform_send_display_prompt_status_textid(listener, "skinny_server.c" , (const char *)__func__, 754, 0, SKINNY_TEXTID_IN_USE_REMOTE , line_instance, helper->tech_pvt->call_id); | |||
| 755 | ||||
| 756 | send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, line_instance, helper->tech_pvt->call_id)perform_send_set_ringer(listener, "skinny_server.c", (const char *)__func__, 756, SKINNY_RING_OFF, SKINNY_RING_FOREVER, line_instance , helper->tech_pvt->call_id); | |||
| 757 | } | |||
| 758 | } | |||
| 759 | return 0; | |||
| 760 | } | |||
| 761 | ||||
| 762 | switch_status_t skinny_session_answer(switch_core_session_t *session, listener_t *listener, uint32_t line_instance) | |||
| 763 | { | |||
| 764 | struct skinny_session_answer_helper helper = {0}; | |||
| 765 | switch_channel_t *channel = NULL((void*)0); | |||
| 766 | private_t *tech_pvt = NULL((void*)0); | |||
| 767 | ||||
| 768 | switch_assert(session)((session) ? (void) (0) : __assert_fail ("session", "skinny_server.c" , 768, __PRETTY_FUNCTION__)); | |||
| 769 | switch_assert(listener)((listener) ? (void) (0) : __assert_fail ("listener", "skinny_server.c" , 769, __PRETTY_FUNCTION__)); | |||
| 770 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 770, __PRETTY_FUNCTION__)); | |||
| 771 | ||||
| 772 | skinny_hold_active_calls(listener); | |||
| 773 | ||||
| 774 | channel = switch_core_session_get_channel(session); | |||
| 775 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 776 | ||||
| 777 | send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, line_instance, tech_pvt->call_id)perform_send_set_ringer(listener, "skinny_server.c", (const char *)__func__, 777, SKINNY_RING_OFF, SKINNY_RING_FOREVER, line_instance , tech_pvt->call_id); | |||
| 778 | send_set_speaker_mode(listener, SKINNY_SPEAKER_ON)perform_send_set_speaker_mode(listener, "skinny_server.c", (const char *)__func__, 778, SKINNY_SPEAKER_ON); | |||
| 779 | send_set_lamp(listener, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_ON)perform_send_set_lamp(listener, "skinny_server.c", (const char *)__func__, 779, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_ON ); | |||
| 780 | skinny_line_set_state(listener, line_instance, tech_pvt->call_id, SKINNY_OFF_HOOK)skinny_line_perform_set_state("skinny_server.c", (const char * )__func__, 780, listener, line_instance, tech_pvt->call_id , SKINNY_OFF_HOOK); | |||
| 781 | send_activate_call_plane(listener, line_instance)perform_send_activate_call_plane(listener, "skinny_server.c", (const char *)__func__, 781, line_instance); | |||
| 782 | ||||
| 783 | helper.tech_pvt = tech_pvt; | |||
| 784 | helper.listener = listener; | |||
| 785 | helper.line_instance = line_instance; | |||
| 786 | ||||
| 787 | skinny_session_walk_lines(tech_pvt->profile, switch_core_session_get_uuid(session), skinny_session_answer_callback, &helper); | |||
| 788 | ||||
| 789 | if (switch_channel_get_state(channel) == CS_INIT) { | |||
| 790 | switch_channel_set_state(channel, CS_ROUTING)switch_channel_perform_set_state(channel, "skinny_server.c", ( const char *)__func__, 790, CS_ROUTING); | |||
| 791 | } | |||
| 792 | skinny_session_start_media(session, listener, line_instance); | |||
| 793 | ||||
| 794 | return SWITCH_STATUS_SUCCESS; | |||
| 795 | } | |||
| 796 | ||||
| 797 | switch_status_t skinny_session_start_media(switch_core_session_t *session, listener_t *listener, uint32_t line_instance) | |||
| 798 | { | |||
| 799 | switch_channel_t *channel = NULL((void*)0); | |||
| 800 | private_t *tech_pvt = NULL((void*)0); | |||
| 801 | ||||
| 802 | switch_assert(session)((session) ? (void) (0) : __assert_fail ("session", "skinny_server.c" , 802, __PRETTY_FUNCTION__)); | |||
| 803 | switch_assert(listener)((listener) ? (void) (0) : __assert_fail ("listener", "skinny_server.c" , 803, __PRETTY_FUNCTION__)); | |||
| 804 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 804, __PRETTY_FUNCTION__)); | |||
| 805 | ||||
| 806 | channel = switch_core_session_get_channel(session); | |||
| 807 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 808 | ||||
| 809 | if (!switch_channel_test_flag(channel, CF_EARLY_MEDIA)) { | |||
| 810 | send_stop_tone(listener, line_instance, tech_pvt->call_id)perform_send_stop_tone(listener, "skinny_server.c", (const char *)__func__, 810, line_instance, tech_pvt->call_id); | |||
| 811 | send_open_receive_channel(listener,perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 820, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 812 | tech_pvt->call_id, /* uint32_t conference_id, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 820, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 813 | tech_pvt->call_id, /* uint32_t pass_thru_party_id, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 820, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 814 | SKINNY_PTIME, /* uint32_t ms_per_packet, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 820, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 815 | SKINNY_CODEC_ULAW_64K, /* uint32_t payload_capacity, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 820, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 816 | 0, /* uint32_t echo_cancel_type, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 820, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 817 | 0, /* uint32_t g723_bitrate, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 820, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 818 | tech_pvt->call_id, /* uint32_t conference_id2, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 820, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 819 | 0 /* uint32_t reserved[10] */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 820, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 820 | )perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 820, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0); | |||
| 821 | } | |||
| 822 | if (!switch_test_flag(tech_pvt, TFLAG_EARLY_MEDIA)((tech_pvt)->flags & TFLAG_EARLY_MEDIA)) { | |||
| 823 | skinny_line_set_state(listener, line_instance, tech_pvt->call_id, SKINNY_CONNECTED)skinny_line_perform_set_state("skinny_server.c", (const char * )__func__, 823, listener, line_instance, tech_pvt->call_id , SKINNY_CONNECTED); | |||
| 824 | send_select_soft_keys(listener, line_instance, tech_pvt->call_id,perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 825, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_CONNECTED , 0xffff) | |||
| 825 | SKINNY_KEY_SET_CONNECTED, 0xffff)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 825, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_CONNECTED , 0xffff); | |||
| 826 | ||||
| 827 | send_display_prompt_status_textid(listener, 0, SKINNY_TEXTID_CONNECTED, line_instance, tech_pvt->call_id)perform_send_display_prompt_status_textid(listener, "skinny_server.c" , (const char *)__func__, 827, 0, SKINNY_TEXTID_CONNECTED, line_instance , tech_pvt->call_id); | |||
| 828 | } | |||
| 829 | skinny_session_send_call_info(session, listener, line_instance); | |||
| 830 | ||||
| 831 | return SWITCH_STATUS_SUCCESS; | |||
| 832 | } | |||
| 833 | ||||
| 834 | switch_status_t skinny_session_hold_line(switch_core_session_t *session, listener_t *listener, uint32_t line_instance) | |||
| 835 | { | |||
| 836 | private_t *tech_pvt = NULL((void*)0); | |||
| 837 | ||||
| 838 | switch_assert(session)((session) ? (void) (0) : __assert_fail ("session", "skinny_server.c" , 838, __PRETTY_FUNCTION__)); | |||
| 839 | switch_assert(listener)((listener) ? (void) (0) : __assert_fail ("listener", "skinny_server.c" , 839, __PRETTY_FUNCTION__)); | |||
| 840 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 840, __PRETTY_FUNCTION__)); | |||
| 841 | ||||
| 842 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 843 | ||||
| 844 | skinny_session_stop_media(session, listener, line_instance); | |||
| 845 | switch_ivr_hold(session, NULL((void*)0), 1); | |||
| 846 | ||||
| 847 | send_define_current_time_date(listener)perform_send_define_current_time_date(listener, "skinny_server.c" , (const char *)__func__, 847); | |||
| 848 | send_set_lamp(listener, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_WINK)perform_send_set_lamp(listener, "skinny_server.c", (const char *)__func__, 848, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_WINK ); | |||
| 849 | skinny_line_set_state(listener, line_instance, tech_pvt->call_id, SKINNY_HOLD)skinny_line_perform_set_state("skinny_server.c", (const char * )__func__, 849, listener, line_instance, tech_pvt->call_id , SKINNY_HOLD); | |||
| 850 | send_select_soft_keys(listener, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_ON_HOLD, 0xffff)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 850, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_ON_HOLD , 0xffff); | |||
| 851 | ||||
| 852 | send_display_prompt_status_textid(listener, 0, SKINNY_TEXTID_HOLD, line_instance, tech_pvt->call_id)perform_send_display_prompt_status_textid(listener, "skinny_server.c" , (const char *)__func__, 852, 0, SKINNY_TEXTID_HOLD, line_instance , tech_pvt->call_id); | |||
| 853 | ||||
| 854 | skinny_session_send_call_info(tech_pvt->session, listener, line_instance); | |||
| 855 | send_set_speaker_mode(listener, SKINNY_SPEAKER_OFF)perform_send_set_speaker_mode(listener, "skinny_server.c", (const char *)__func__, 855, SKINNY_SPEAKER_OFF); | |||
| 856 | send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, line_instance, tech_pvt->call_id)perform_send_set_ringer(listener, "skinny_server.c", (const char *)__func__, 856, SKINNY_RING_OFF, SKINNY_RING_FOREVER, line_instance , tech_pvt->call_id); | |||
| 857 | ||||
| 858 | return SWITCH_STATUS_SUCCESS; | |||
| 859 | } | |||
| 860 | ||||
| 861 | switch_status_t skinny_session_unhold_line(switch_core_session_t *session, listener_t *listener, uint32_t line_instance) | |||
| 862 | { | |||
| 863 | private_t *tech_pvt = NULL((void*)0); | |||
| 864 | ||||
| 865 | switch_assert(session)((session) ? (void) (0) : __assert_fail ("session", "skinny_server.c" , 865, __PRETTY_FUNCTION__)); | |||
| 866 | switch_assert(listener)((listener) ? (void) (0) : __assert_fail ("listener", "skinny_server.c" , 866, __PRETTY_FUNCTION__)); | |||
| 867 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 867, __PRETTY_FUNCTION__)); | |||
| 868 | ||||
| 869 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 870 | ||||
| 871 | skinny_hold_active_calls(listener); | |||
| 872 | send_set_ringer(listener, SKINNY_RING_OFF, SKINNY_RING_FOREVER, line_instance, tech_pvt->call_id)perform_send_set_ringer(listener, "skinny_server.c", (const char *)__func__, 872, SKINNY_RING_OFF, SKINNY_RING_FOREVER, line_instance , tech_pvt->call_id); | |||
| 873 | send_set_speaker_mode(listener, SKINNY_SPEAKER_ON)perform_send_set_speaker_mode(listener, "skinny_server.c", (const char *)__func__, 873, SKINNY_SPEAKER_ON); | |||
| 874 | send_select_soft_keys(listener, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_RING_OUT, 0xffff)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 874, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_RING_OUT , 0xffff); | |||
| 875 | ||||
| 876 | send_stop_tone(listener, line_instance, tech_pvt->call_id)perform_send_stop_tone(listener, "skinny_server.c", (const char *)__func__, 876, line_instance, tech_pvt->call_id); | |||
| 877 | send_open_receive_channel(listener,perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 886, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 878 | tech_pvt->call_id, /* uint32_t conference_id, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 886, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 879 | tech_pvt->call_id, /* uint32_t pass_thru_party_id, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 886, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 880 | SKINNY_PTIME, /* uint32_t ms_per_packet, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 886, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 881 | SKINNY_CODEC_ULAW_64K, /* uint32_t payload_capacity, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 886, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 882 | 0, /* uint32_t echo_cancel_type, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 886, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 883 | 0, /* uint32_t g723_bitrate, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 886, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 884 | tech_pvt->call_id, /* uint32_t conference_id2, */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 886, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 885 | 0 /* uint32_t reserved[10] */perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 886, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0) | |||
| 886 | )perform_send_open_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 886, tech_pvt->call_id, tech_pvt ->call_id, 20, SKINNY_CODEC_ULAW_64K, 0, 0, tech_pvt->call_id , 0); | |||
| 887 | ||||
| 888 | skinny_line_set_state(listener, line_instance, tech_pvt->call_id, SKINNY_CONNECTED)skinny_line_perform_set_state("skinny_server.c", (const char * )__func__, 888, listener, line_instance, tech_pvt->call_id , SKINNY_CONNECTED); | |||
| 889 | send_select_soft_keys(listener, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_CONNECTED, 0xffff)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 889, line_instance, tech_pvt->call_id, SKINNY_KEY_SET_CONNECTED , 0xffff); | |||
| 890 | ||||
| 891 | send_display_prompt_status_textid(listener, 0, SKINNY_TEXTID_CONNECTED, line_instance, tech_pvt->call_id)perform_send_display_prompt_status_textid(listener, "skinny_server.c" , (const char *)__func__, 891, 0, SKINNY_TEXTID_CONNECTED, line_instance , tech_pvt->call_id); | |||
| 892 | skinny_session_send_call_info(session, listener, line_instance); | |||
| 893 | ||||
| 894 | return SWITCH_STATUS_SUCCESS; | |||
| 895 | } | |||
| 896 | ||||
| 897 | switch_status_t skinny_session_transfer(switch_core_session_t *session, listener_t *listener, uint32_t line_instance) | |||
| 898 | { | |||
| 899 | switch_status_t status = SWITCH_STATUS_SUCCESS; | |||
| 900 | private_t *tech_pvt = NULL((void*)0); | |||
| 901 | switch_channel_t *channel = NULL((void*)0); | |||
| 902 | switch_channel_t *channel2 = NULL((void*)0); | |||
| 903 | const char *local_uuid = NULL((void*)0); | |||
| 904 | const char *local_uuid2 = NULL((void*)0); | |||
| 905 | const char *remote_uuid = NULL((void*)0); | |||
| 906 | const char *remote_uuid2 = NULL((void*)0); | |||
| 907 | switch_core_session_t *session2 = NULL((void*)0); | |||
| 908 | switch_core_session_t *rsession = NULL((void*)0); | |||
| 909 | private_t *tech_pvt2 = NULL((void*)0); | |||
| 910 | ||||
| 911 | switch_assert(session)((session) ? (void) (0) : __assert_fail ("session", "skinny_server.c" , 911, __PRETTY_FUNCTION__)); | |||
| 912 | switch_assert(listener)((listener) ? (void) (0) : __assert_fail ("listener", "skinny_server.c" , 912, __PRETTY_FUNCTION__)); | |||
| 913 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 913, __PRETTY_FUNCTION__)); | |||
| 914 | ||||
| 915 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 916 | channel = switch_core_session_get_channel(session); | |||
| 917 | local_uuid = switch_channel_get_uuid(channel); | |||
| 918 | remote_uuid = switch_channel_get_partner_uuid(channel); | |||
| 919 | ||||
| 920 | if ( switch_core_session_get_partner(session, &rsession)switch_core_session_perform_get_partner(session, &rsession , "skinny_server.c", (const char *)__func__, 920) == SWITCH_STATUS_SUCCESS ) | |||
| 921 | { | |||
| 922 | switch_channel_t *rchannel = NULL((void*)0); | |||
| 923 | rchannel = switch_core_session_get_channel(rsession); | |||
| 924 | ||||
| 925 | skinny_log_l_msg(listener, SWITCH_LOG_INFO, "SST: setting uuid bridge continue flag on remote channel\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 925, ((void*)0), SWITCH_LOG_INFO, "[%s:%d @ %s:%d] " "SST: setting uuid bridge continue flag on remote channel\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 926 | ||||
| 927 | switch_channel_set_variable(rchannel, "uuid_bridge_continue_on_cancel", "true")switch_channel_set_variable_var_check(rchannel, "uuid_bridge_continue_on_cancel" , "true", SWITCH_TRUE); | |||
| 928 | switch_core_session_rwunlock(rsession); | |||
| 929 | } | |||
| 930 | ||||
| 931 | skinny_log_l(listener, SWITCH_LOG_INFO, "SST: local_uuid=%s remote_uuid=%s\n", local_uuid, remote_uuid)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 931, ((void*)0), SWITCH_LOG_INFO, "[%s:%d @ %s:%d] " "SST: local_uuid=%s remote_uuid=%s\n", (_zstr(listener->device_name ) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port, local_uuid, remote_uuid); | |||
| 932 | ||||
| 933 | if (tech_pvt->transfer_from_call_id) { | |||
| 934 | skinny_log_l_msg(listener, SWITCH_LOG_INFO, "SST: transfer_from_call_id\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 934, ((void*)0), SWITCH_LOG_INFO, "[%s:%d @ %s:%d] " "SST: transfer_from_call_id\n", (_zstr(listener->device_name ) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port); | |||
| 935 | ||||
| 936 | if((session2 = skinny_profile_find_session(listener->profile, listener, &line_instance, tech_pvt->transfer_from_call_id))) { | |||
| 937 | channel2 = switch_core_session_get_channel(session2); | |||
| 938 | local_uuid2 = switch_channel_get_uuid(channel2); | |||
| 939 | remote_uuid2 = switch_channel_get_partner_uuid(channel2); | |||
| 940 | skinny_log_ls(listener, session2, SWITCH_LOG_INFO, "SST: tx from session - local_uuid=%s remote_uuid=%s local_uuid2=%s remote_uuid2=%s\n",switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 941, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: tx from session - local_uuid=%s remote_uuid=%s local_uuid2=%s remote_uuid2=%s\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, local_uuid, remote_uuid, local_uuid2, remote_uuid2 ) | |||
| 941 | local_uuid, remote_uuid, local_uuid2, remote_uuid2)switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 941, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: tx from session - local_uuid=%s remote_uuid=%s local_uuid2=%s remote_uuid2=%s\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, local_uuid, remote_uuid, local_uuid2, remote_uuid2 ); | |||
| 942 | ||||
| 943 | skinny_log_ls(listener, session2, SWITCH_LOG_INFO, "SST: attempting ivr bridge from (%s) to (%s)\n", remote_uuid, remote_uuid2)switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 943, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: attempting ivr bridge from (%s) to (%s)\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, remote_uuid, remote_uuid2); | |||
| 944 | ||||
| 945 | if (switch_ivr_uuid_bridge(remote_uuid2, remote_uuid) == SWITCH_STATUS_SUCCESS) { | |||
| 946 | skinny_log_ls_msg(listener, session2, SWITCH_LOG_INFO, "SST: success on uuid bridge\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 946, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: success on uuid bridge\n", (_zstr( listener->device_name) ? "_undef_" : listener->device_name ), listener->device_instance, (_zstr(listener->remote_ip ) ? "_undef_" : listener->remote_ip), listener->remote_port ); | |||
| 947 | ||||
| 948 | switch_channel_hangup(channel, SWITCH_CAUSE_NORMAL_CLEARING)switch_channel_perform_hangup(channel, "skinny_server.c", (const char *)__func__, 948, SWITCH_CAUSE_NORMAL_CLEARING); | |||
| 949 | switch_channel_hangup(channel2, SWITCH_CAUSE_NORMAL_CLEARING)switch_channel_perform_hangup(channel2, "skinny_server.c", (const char *)__func__, 949, SWITCH_CAUSE_NORMAL_CLEARING); | |||
| 950 | } else { | |||
| 951 | skinny_log_ls_msg(listener, session2, SWITCH_LOG_INFO, "SST: failure on uuid bridge\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 951, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: failure on uuid bridge\n", (_zstr( listener->device_name) ? "_undef_" : listener->device_name ), listener->device_instance, (_zstr(listener->remote_ip ) ? "_undef_" : listener->remote_ip), listener->remote_port ); | |||
| 952 | /* TODO: How to inform the user that the bridge is not possible? */ | |||
| 953 | } | |||
| 954 | switch_core_session_rwunlock(session2); | |||
| 955 | } | |||
| 956 | } else { | |||
| 957 | skinny_log_l_msg(listener, SWITCH_LOG_INFO, "SST: !transfer_from_call_id\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 957, ((void*)0), SWITCH_LOG_INFO, "[%s:%d @ %s:%d] " "SST: !transfer_from_call_id\n", (_zstr(listener->device_name ) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port); | |||
| 958 | ||||
| 959 | if(remote_uuid) { | |||
| 960 | skinny_log_ls_msg(listener, session2, SWITCH_LOG_INFO, "SST: found remote_uuid\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 960, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: found remote_uuid\n", (_zstr(listener ->device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port); | |||
| 961 | ||||
| 962 | /* TODO CallSelectStat */ | |||
| 963 | skinny_log_ls_msg(listener, session2, SWITCH_LOG_INFO, "SST: creating incoming session\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 963, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: creating incoming session\n", (_zstr (listener->device_name) ? "_undef_" : listener->device_name ), listener->device_instance, (_zstr(listener->remote_ip ) ? "_undef_" : listener->remote_ip), listener->remote_port ); | |||
| 964 | status = skinny_create_incoming_session(listener, &line_instance, &session2); | |||
| 965 | if ( ! session2 ) { | |||
| 966 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "SST: Unable to create incoming session for transfer.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 966, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "SST: Unable to create incoming session for transfer.\n", (_zstr (listener->device_name) ? "_undef_" : listener->device_name ), listener->device_instance, (_zstr(listener->remote_ip ) ? "_undef_" : listener->remote_ip), listener->remote_port ); | |||
| 967 | return SWITCH_STATUS_FALSE; | |||
| 968 | } | |||
| 969 | tech_pvt2 = switch_core_session_get_private(session2)switch_core_session_get_private_class(session2, SWITCH_PVT_PRIMARY ); | |||
| 970 | tech_pvt2->transfer_from_call_id = tech_pvt->call_id; | |||
| 971 | tech_pvt->transfer_to_call_id = tech_pvt2->call_id; | |||
| 972 | skinny_log_ls(listener, session2, SWITCH_LOG_INFO, "SST: transfer_to_call_id=%d transfer_from_call_id=%d\n", tech_pvt2->call_id,switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 973, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: transfer_to_call_id=%d transfer_from_call_id=%d\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, tech_pvt2->call_id, tech_pvt->call_id) | |||
| 973 | tech_pvt->call_id)switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 973, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: transfer_to_call_id=%d transfer_from_call_id=%d\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, tech_pvt2->call_id, tech_pvt->call_id); | |||
| 974 | skinny_log_ls_msg(listener, session2, SWITCH_LOG_INFO, "SST: triggering dial on incoming session\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 974, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: triggering dial on incoming session\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 975 | skinny_session_process_dest(session2, listener, line_instance, NULL((void*)0), '\0', 0); | |||
| 976 | ||||
| 977 | channel2 = switch_core_session_get_channel(session2); | |||
| 978 | local_uuid2 = switch_channel_get_uuid(channel2); | |||
| 979 | remote_uuid2 = switch_channel_get_partner_uuid(channel2); | |||
| 980 | skinny_log_ls(listener, session2, SWITCH_LOG_INFO, "SST: new session - local_uuid2=%s remote_uuid2=%s\n", local_uuid2, remote_uuid2)switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 980, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: new session - local_uuid2=%s remote_uuid2=%s\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, local_uuid2, remote_uuid2); | |||
| 981 | ||||
| 982 | switch_core_session_rwunlock(session2); | |||
| 983 | } else { | |||
| 984 | skinny_log_ls_msg(listener, session2, SWITCH_LOG_INFO, "SST: could not find remote_uuid\n")switch_log_printf(SWITCH_CHANNEL_ID_SESSION, "skinny_server.c" , (const char *)__func__, 984, (const char*)(session2), SWITCH_LOG_INFO , "[%s:%d @ %s:%d] " "SST: could not find remote_uuid\n", (_zstr (listener->device_name) ? "_undef_" : listener->device_name ), listener->device_instance, (_zstr(listener->remote_ip ) ? "_undef_" : listener->remote_ip), listener->remote_port ); | |||
| 985 | ||||
| 986 | /* TODO: How to inform the user that the bridge is not possible? */ | |||
| 987 | } | |||
| 988 | } | |||
| 989 | return status; | |||
| 990 | } | |||
| 991 | ||||
| 992 | switch_status_t skinny_session_stop_media(switch_core_session_t *session, listener_t *listener, uint32_t line_instance) | |||
| 993 | { | |||
| 994 | private_t *tech_pvt = NULL((void*)0); | |||
| 995 | ||||
| 996 | switch_assert(session)((session) ? (void) (0) : __assert_fail ("session", "skinny_server.c" , 996, __PRETTY_FUNCTION__)); | |||
| 997 | switch_assert(listener)((listener) ? (void) (0) : __assert_fail ("listener", "skinny_server.c" , 997, __PRETTY_FUNCTION__)); | |||
| 998 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 998, __PRETTY_FUNCTION__)); | |||
| 999 | ||||
| 1000 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 1001 | ||||
| 1002 | switch_clear_flag_locked(tech_pvt, TFLAG_IO)switch_mutex_lock(tech_pvt->flag_mutex); (tech_pvt)->flags &= ~(TFLAG_IO); switch_mutex_unlock(tech_pvt->flag_mutex );; | |||
| 1003 | ||||
| 1004 | send_close_receive_channel(listener,perform_send_close_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 1008, tech_pvt->call_id, tech_pvt ->party_id, tech_pvt->call_id) | |||
| 1005 | tech_pvt->call_id, /* uint32_t conference_id, */perform_send_close_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 1008, tech_pvt->call_id, tech_pvt ->party_id, tech_pvt->call_id) | |||
| 1006 | tech_pvt->party_id, /* uint32_t pass_thru_party_id, */perform_send_close_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 1008, tech_pvt->call_id, tech_pvt ->party_id, tech_pvt->call_id) | |||
| 1007 | tech_pvt->call_id /* uint32_t conference_id2, */perform_send_close_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 1008, tech_pvt->call_id, tech_pvt ->party_id, tech_pvt->call_id) | |||
| 1008 | )perform_send_close_receive_channel(listener, "skinny_server.c" , (const char *)__func__, 1008, tech_pvt->call_id, tech_pvt ->party_id, tech_pvt->call_id); | |||
| 1009 | send_stop_media_transmission(listener,perform_send_stop_media_transmission(listener, "skinny_server.c" , (const char *)__func__, 1013, tech_pvt->call_id, tech_pvt ->party_id, tech_pvt->call_id) | |||
| 1010 | tech_pvt->call_id, /* uint32_t conference_id, */perform_send_stop_media_transmission(listener, "skinny_server.c" , (const char *)__func__, 1013, tech_pvt->call_id, tech_pvt ->party_id, tech_pvt->call_id) | |||
| 1011 | tech_pvt->party_id, /* uint32_t pass_thru_party_id, */perform_send_stop_media_transmission(listener, "skinny_server.c" , (const char *)__func__, 1013, tech_pvt->call_id, tech_pvt ->party_id, tech_pvt->call_id) | |||
| 1012 | tech_pvt->call_id /* uint32_t conference_id2, */perform_send_stop_media_transmission(listener, "skinny_server.c" , (const char *)__func__, 1013, tech_pvt->call_id, tech_pvt ->party_id, tech_pvt->call_id) | |||
| 1013 | )perform_send_stop_media_transmission(listener, "skinny_server.c" , (const char *)__func__, 1013, tech_pvt->call_id, tech_pvt ->party_id, tech_pvt->call_id); | |||
| 1014 | ||||
| 1015 | return SWITCH_STATUS_SUCCESS; | |||
| 1016 | } | |||
| 1017 | ||||
| 1018 | struct skinny_hold_active_calls_helper { | |||
| 1019 | listener_t *listener; | |||
| 1020 | }; | |||
| 1021 | ||||
| 1022 | int skinny_hold_active_calls_callback(void *pArg, int argc, char **argv, char **columnNames) | |||
| 1023 | { | |||
| 1024 | struct skinny_hold_active_calls_helper *helper = pArg; | |||
| 1025 | switch_core_session_t *session; | |||
| 1026 | ||||
| 1027 | /* char *device_name = argv[0]; */ | |||
| 1028 | /* uint32_t device_instance = atoi(argv[1]); */ | |||
| 1029 | /* uint32_t position = atoi(argv[2]); */ | |||
| 1030 | uint32_t line_instance = atoi(argv[3]); | |||
| 1031 | /* char *label = argv[4]; */ | |||
| 1032 | /* char *value = argv[5]; */ | |||
| 1033 | /* char *caller_name = argv[6]; */ | |||
| 1034 | /* uint32_t ring_on_idle = atoi(argv[7]); */ | |||
| 1035 | /* uint32_t ring_on_active = atoi(argv[8]); */ | |||
| 1036 | /* uint32_t busy_trigger = atoi(argv[9]); */ | |||
| 1037 | /* char *forward_all = argv[10]; */ | |||
| 1038 | /* char *forward_busy = argv[11]; */ | |||
| 1039 | /* char *forward_noanswer = argv[12]; */ | |||
| 1040 | /* uint32_t noanswer_duration = atoi(argv[13]); */ | |||
| 1041 | /* char *channel_uuid = argv[14]; */ | |||
| 1042 | uint32_t call_id = atoi(argv[15]); | |||
| 1043 | /* uint32_t call_state = atoi(argv[16]); */ | |||
| 1044 | ||||
| 1045 | session = skinny_profile_find_session(helper->listener->profile, helper->listener, &line_instance, call_id); | |||
| 1046 | ||||
| 1047 | if(session) { | |||
| 1048 | skinny_session_hold_line(session, helper->listener, line_instance); | |||
| 1049 | switch_core_session_rwunlock(session); | |||
| 1050 | } | |||
| 1051 | ||||
| 1052 | return 0; | |||
| 1053 | } | |||
| 1054 | ||||
| 1055 | switch_status_t skinny_hold_active_calls(listener_t *listener) | |||
| 1056 | { | |||
| 1057 | struct skinny_hold_active_calls_helper helper = {0}; | |||
| 1058 | char *sql; | |||
| 1059 | ||||
| 1060 | helper.listener = listener; | |||
| 1061 | ||||
| 1062 | if ((sql = switch_mprintf( | |||
| 1063 | "SELECT skinny_lines.*, channel_uuid, call_id, call_state " | |||
| 1064 | "FROM skinny_active_lines " | |||
| 1065 | "INNER JOIN skinny_lines " | |||
| 1066 | "ON skinny_active_lines.device_name = skinny_lines.device_name " | |||
| 1067 | "AND skinny_active_lines.device_instance = skinny_lines.device_instance " | |||
| 1068 | "AND skinny_active_lines.line_instance = skinny_lines.line_instance " | |||
| 1069 | "WHERE skinny_lines.device_name='%s' AND skinny_lines.device_instance=%d AND (call_state=%d OR call_state=%d)", | |||
| 1070 | listener->device_name, listener->device_instance, SKINNY_PROCEED, SKINNY_CONNECTED))) { | |||
| 1071 | skinny_execute_sql_callback(listener->profile, listener->profile->sql_mutex, sql, skinny_hold_active_calls_callback, &helper); | |||
| 1072 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 1073 | } | |||
| 1074 | ||||
| 1075 | return SWITCH_STATUS_SUCCESS; | |||
| 1076 | } | |||
| 1077 | ||||
| 1078 | /*****************************************************************************/ | |||
| 1079 | /* SKINNY MESSAGE HANDLERS */ | |||
| 1080 | /*****************************************************************************/ | |||
| 1081 | switch_status_t skinny_handle_keep_alive_message(listener_t *listener, skinny_message_t *request) | |||
| 1082 | { | |||
| 1083 | keepalive_listener(listener, NULL((void*)0)); | |||
| 1084 | ||||
| 1085 | send_keep_alive_ack(listener)perform_send_keep_alive_ack(listener, "skinny_server.c", (const char *)__func__, 1085);; | |||
| 1086 | ||||
| 1087 | return SWITCH_STATUS_SUCCESS; | |||
| 1088 | } | |||
| 1089 | ||||
| 1090 | switch_status_t skinny_handle_register(listener_t *listener, skinny_message_t *request) | |||
| 1091 | { | |||
| 1092 | switch_status_t status = SWITCH_STATUS_FALSE; | |||
| 1093 | skinny_profile_t *profile; | |||
| 1094 | switch_event_t *event = NULL((void*)0); | |||
| 1095 | switch_event_t *params = NULL((void*)0); | |||
| 1096 | switch_xml_t xroot, xdomain, xgroup, xuser, xskinny, xparams, xparam, xbuttons, xbutton; | |||
| 1097 | listener_t *listener2 = NULL((void*)0); | |||
| 1098 | char *sql; | |||
| 1099 | assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 1099, __PRETTY_FUNCTION__)); | |||
| 1100 | profile = listener->profile; | |||
| 1101 | ||||
| 1102 | skinny_check_data_length(request, sizeof(request->data.reg))if (request->length < sizeof(request->data.reg)+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1102, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.reg)+4 ); return SWITCH_STATUS_FALSE; }; | |||
| 1103 | ||||
| 1104 | if (!zstr(listener->device_name)_zstr(listener->device_name)) { | |||
| 1105 | switch_log_printf(SWITCH_CHANNEL_LOGSWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 1105, ((void*)0), SWITCH_LOG_ERROR, | |||
| 1106 | "A device is already registered on this listener.\n"); | |||
| 1107 | send_register_reject(listener, "A device is already registered on this listener")perform_send_register_reject(listener, "skinny_server.c", (const char *)__func__, 1107, "A device is already registered on this listener" ); | |||
| 1108 | return SWITCH_STATUS_FALSE; | |||
| 1109 | } | |||
| 1110 | ||||
| 1111 | /* Check directory */ | |||
| 1112 | skinny_device_event(listener, ¶ms, SWITCH_EVENT_REQUEST_PARAMS, SWITCH_EVENT_SUBCLASS_ANY((void*)0)); | |||
| 1113 | switch_event_add_header_string(params, SWITCH_STACK_BOTTOM, "action", "skinny-auth"); | |||
| 1114 | ||||
| 1115 | /* clean up all traces before adding to database */ | |||
| 1116 | skinny_clean_device_from_db(listener, request->data.reg.device_name); | |||
| 1117 | ||||
| 1118 | if (switch_xml_locate_user("id", request->data.reg.device_name, profile->domain, "", &xroot, &xdomain, &xuser, &xgroup, params) != SWITCH_STATUS_SUCCESS) { | |||
| 1119 | switch_log_printf(SWITCH_CHANNEL_LOGSWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 1119, ((void*)0), SWITCH_LOG_WARNING, "Can't find device [%s@%s]\n" | |||
| 1120 | "You must define a domain called '%s' in your directory and add a user with id=\"%s\".\n" | |||
| 1121 | , request->data.reg.device_name, profile->domain, profile->domain, request->data.reg.device_name); | |||
| 1122 | send_register_reject(listener, "Device not found")perform_send_register_reject(listener, "skinny_server.c", (const char *)__func__, 1122, "Device not found"); | |||
| 1123 | status = SWITCH_STATUS_FALSE; | |||
| 1124 | goto end; | |||
| 1125 | } | |||
| 1126 | ||||
| 1127 | /* we clean up device above, so this below block will never trigger. I don't | |||
| 1128 | know the full details of why there would be multiple listeners with | |||
| 1129 | the same device - maybe a VGC or similar? Not really high priority for | |||
| 1130 | support at the moment, but may need to revisit this later */ | |||
| 1131 | ||||
| 1132 | skinny_profile_find_listener_by_device_name_and_instance(listener->profile, | |||
| 1133 | request->data.reg.device_name, request->data.reg.instance, &listener2); | |||
| 1134 | if (listener2) { | |||
| 1135 | switch_log_printf(SWITCH_CHANNEL_LOGSWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 1135, ((void*)0), SWITCH_LOG_ERROR, | |||
| 1136 | "Device %s:%d is already registered on another listener.\n", | |||
| 1137 | request->data.reg.device_name, request->data.reg.instance); | |||
| 1138 | send_register_reject(listener, "Device is already registered on another listener")perform_send_register_reject(listener, "skinny_server.c", (const char *)__func__, 1138, "Device is already registered on another listener" ); | |||
| 1139 | status = SWITCH_STATUS_FALSE; | |||
| 1140 | goto end; | |||
| 1141 | } | |||
| 1142 | ||||
| 1143 | if ((sql = switch_mprintf( | |||
| 1144 | "INSERT INTO skinny_devices " | |||
| 1145 | "(name, user_id, instance, ip, type, max_streams, codec_string) " | |||
| 1146 | "VALUES ('%q','%d','%d', '%q', '%d', '%d', '%q')", | |||
| 1147 | request->data.reg.device_name, | |||
| 1148 | request->data.reg.user_id, | |||
| 1149 | request->data.reg.instance, | |||
| 1150 | inet_ntoa(request->data.reg.ip), | |||
| 1151 | request->data.reg.device_type, | |||
| 1152 | request->data.reg.max_streams, | |||
| 1153 | "" /* codec_string */ | |||
| 1154 | ))) { | |||
| 1155 | skinny_execute_sql(profile, sql, profile->sql_mutex); | |||
| 1156 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 1157 | } | |||
| 1158 | ||||
| 1159 | ||||
| 1160 | switch_copy_string(listener->device_name, request->data.reg.device_name, 16); | |||
| 1161 | listener->device_instance = request->data.reg.instance; | |||
| 1162 | listener->device_type = request->data.reg.device_type; | |||
| 1163 | ||||
| 1164 | xskinny = switch_xml_child(xuser, "skinny"); | |||
| 1165 | if (xskinny) { | |||
| 1166 | if ((xparams = switch_xml_child(xskinny, "params"))) { | |||
| 1167 | for (xparam = switch_xml_child(xparams, "param"); xparam; xparam = xparam->next) { | |||
| 1168 | const char *name = switch_xml_attr_soft(xparam, "name"); | |||
| 1169 | const char *value = switch_xml_attr_soft(xparam, "value"); | |||
| 1170 | if (!strcasecmp(name, "skinny-firmware-version")) { | |||
| 1171 | switch_copy_string(listener->firmware_version, value, 16); | |||
| 1172 | } else if (!strcasecmp(name, "skinny-soft-key-set-set")) { | |||
| 1173 | listener->soft_key_set_set = switch_core_strdup(profile->pool, value)switch_core_perform_strdup(profile->pool, value, "skinny_server.c" , (const char *)__func__, 1173); | |||
| 1174 | } else if (!strcasecmp(name, "ext-voicemail")) { | |||
| 1175 | if (!listener->ext_voicemail || strcmp(value,listener->ext_voicemail)__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (value) && __builtin_constant_p (listener->ext_voicemail ) && (__s1_len = __builtin_strlen (value), __s2_len = __builtin_strlen (listener->ext_voicemail), (!((size_t)(const void *)((value) + 1) - (size_t)(const void *)(value) == 1) || __s1_len >= 4) && (!((size_t)(const void *)((listener ->ext_voicemail) + 1) - (size_t)(const void *)(listener-> ext_voicemail) == 1) || __s2_len >= 4)) ? __builtin_strcmp (value, listener->ext_voicemail) : (__builtin_constant_p ( value) && ((size_t)(const void *)((value) + 1) - (size_t )(const void *)(value) == 1) && (__s1_len = __builtin_strlen (value), __s1_len < 4) ? (__builtin_constant_p (listener-> ext_voicemail) && ((size_t)(const void *)((listener-> ext_voicemail) + 1) - (size_t)(const void *)(listener->ext_voicemail ) == 1) ? __builtin_strcmp (value, listener->ext_voicemail ) : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (listener->ext_voicemail); int __result = (((const unsigned char *) (const char *) (value))[0] - __s2 [0]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[1] - __s2 [1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[2] - __s2 [2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (value))[3] - __s2[ 3]); } } __result; }))) : (__builtin_constant_p (listener-> ext_voicemail) && ((size_t)(const void *)((listener-> ext_voicemail) + 1) - (size_t)(const void *)(listener->ext_voicemail ) == 1) && (__s2_len = __builtin_strlen (listener-> ext_voicemail), __s2_len < 4) ? (__builtin_constant_p (value ) && ((size_t)(const void *)((value) + 1) - (size_t)( const void *)(value) == 1) ? __builtin_strcmp (value, listener ->ext_voicemail) : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (value); int __result = (((const unsigned char *) (const char *) (listener->ext_voicemail ))[0] - __s2[0]); if (__s2_len > 0 && __result == 0 ) { __result = (((const unsigned char *) (const char *) (listener ->ext_voicemail))[1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (listener->ext_voicemail))[2] - __s2[2]); if (__s2_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (listener->ext_voicemail))[3] - __s2 [3]); } } __result; })))) : __builtin_strcmp (value, listener ->ext_voicemail)))); })) { | |||
| 1176 | listener->ext_voicemail = switch_core_strdup(profile->pool, value)switch_core_perform_strdup(profile->pool, value, "skinny_server.c" , (const char *)__func__, 1176); | |||
| 1177 | } | |||
| 1178 | } else if (!strcasecmp(name, "ext-redial")) { | |||
| 1179 | if (!listener->ext_redial || strcmp(value,listener->ext_redial)__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (value) && __builtin_constant_p (listener->ext_redial ) && (__s1_len = __builtin_strlen (value), __s2_len = __builtin_strlen (listener->ext_redial), (!((size_t)(const void *)((value) + 1) - (size_t)(const void *)(value) == 1) || __s1_len >= 4) && (!((size_t)(const void *)((listener ->ext_redial) + 1) - (size_t)(const void *)(listener->ext_redial ) == 1) || __s2_len >= 4)) ? __builtin_strcmp (value, listener ->ext_redial) : (__builtin_constant_p (value) && ( (size_t)(const void *)((value) + 1) - (size_t)(const void *)( value) == 1) && (__s1_len = __builtin_strlen (value), __s1_len < 4) ? (__builtin_constant_p (listener->ext_redial ) && ((size_t)(const void *)((listener->ext_redial ) + 1) - (size_t)(const void *)(listener->ext_redial) == 1 ) ? __builtin_strcmp (value, listener->ext_redial) : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (listener->ext_redial); int __result = (((const unsigned char *) (const char *) (value))[0] - __s2[0]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[1] - __s2[1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[2] - __s2[2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char * ) (const char *) (value))[3] - __s2[3]); } } __result; }))) : (__builtin_constant_p (listener->ext_redial) && ( (size_t)(const void *)((listener->ext_redial) + 1) - (size_t )(const void *)(listener->ext_redial) == 1) && (__s2_len = __builtin_strlen (listener->ext_redial), __s2_len < 4 ) ? (__builtin_constant_p (value) && ((size_t)(const void *)((value) + 1) - (size_t)(const void *)(value) == 1) ? __builtin_strcmp (value, listener->ext_redial) : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (value); int __result = (((const unsigned char *) (const char *) (listener->ext_redial))[0] - __s2[0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (listener->ext_redial))[1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (listener->ext_redial))[2 ] - __s2[2]); if (__s2_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (listener->ext_redial ))[3] - __s2[3]); } } __result; })))) : __builtin_strcmp (value , listener->ext_redial)))); })) { | |||
| 1180 | listener->ext_redial = switch_core_strdup(profile->pool, value)switch_core_perform_strdup(profile->pool, value, "skinny_server.c" , (const char *)__func__, 1180); | |||
| 1181 | } | |||
| 1182 | } else if (!strcasecmp(name, "ext-meetme")) { | |||
| 1183 | if (!listener->ext_meetme || strcmp(value,listener->ext_meetme)__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (value) && __builtin_constant_p (listener->ext_meetme ) && (__s1_len = __builtin_strlen (value), __s2_len = __builtin_strlen (listener->ext_meetme), (!((size_t)(const void *)((value) + 1) - (size_t)(const void *)(value) == 1) || __s1_len >= 4) && (!((size_t)(const void *)((listener ->ext_meetme) + 1) - (size_t)(const void *)(listener->ext_meetme ) == 1) || __s2_len >= 4)) ? __builtin_strcmp (value, listener ->ext_meetme) : (__builtin_constant_p (value) && ( (size_t)(const void *)((value) + 1) - (size_t)(const void *)( value) == 1) && (__s1_len = __builtin_strlen (value), __s1_len < 4) ? (__builtin_constant_p (listener->ext_meetme ) && ((size_t)(const void *)((listener->ext_meetme ) + 1) - (size_t)(const void *)(listener->ext_meetme) == 1 ) ? __builtin_strcmp (value, listener->ext_meetme) : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (listener->ext_meetme); int __result = (((const unsigned char *) (const char *) (value))[0] - __s2[0]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[1] - __s2[1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[2] - __s2[2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char * ) (const char *) (value))[3] - __s2[3]); } } __result; }))) : (__builtin_constant_p (listener->ext_meetme) && ( (size_t)(const void *)((listener->ext_meetme) + 1) - (size_t )(const void *)(listener->ext_meetme) == 1) && (__s2_len = __builtin_strlen (listener->ext_meetme), __s2_len < 4 ) ? (__builtin_constant_p (value) && ((size_t)(const void *)((value) + 1) - (size_t)(const void *)(value) == 1) ? __builtin_strcmp (value, listener->ext_meetme) : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (value); int __result = (((const unsigned char *) (const char *) (listener->ext_meetme))[0] - __s2[0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (listener->ext_meetme))[1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (listener->ext_meetme))[2 ] - __s2[2]); if (__s2_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (listener->ext_meetme ))[3] - __s2[3]); } } __result; })))) : __builtin_strcmp (value , listener->ext_meetme)))); })) { | |||
| 1184 | listener->ext_meetme = switch_core_strdup(profile->pool, value)switch_core_perform_strdup(profile->pool, value, "skinny_server.c" , (const char *)__func__, 1184); | |||
| 1185 | } | |||
| 1186 | } else if (!strcasecmp(name, "ext-pickup")) { | |||
| 1187 | if (!listener->ext_pickup || strcmp(value,listener->ext_pickup)__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (value) && __builtin_constant_p (listener->ext_pickup ) && (__s1_len = __builtin_strlen (value), __s2_len = __builtin_strlen (listener->ext_pickup), (!((size_t)(const void *)((value) + 1) - (size_t)(const void *)(value) == 1) || __s1_len >= 4) && (!((size_t)(const void *)((listener ->ext_pickup) + 1) - (size_t)(const void *)(listener->ext_pickup ) == 1) || __s2_len >= 4)) ? __builtin_strcmp (value, listener ->ext_pickup) : (__builtin_constant_p (value) && ( (size_t)(const void *)((value) + 1) - (size_t)(const void *)( value) == 1) && (__s1_len = __builtin_strlen (value), __s1_len < 4) ? (__builtin_constant_p (listener->ext_pickup ) && ((size_t)(const void *)((listener->ext_pickup ) + 1) - (size_t)(const void *)(listener->ext_pickup) == 1 ) ? __builtin_strcmp (value, listener->ext_pickup) : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (listener->ext_pickup); int __result = (((const unsigned char *) (const char *) (value))[0] - __s2[0]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[1] - __s2[1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[2] - __s2[2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char * ) (const char *) (value))[3] - __s2[3]); } } __result; }))) : (__builtin_constant_p (listener->ext_pickup) && ( (size_t)(const void *)((listener->ext_pickup) + 1) - (size_t )(const void *)(listener->ext_pickup) == 1) && (__s2_len = __builtin_strlen (listener->ext_pickup), __s2_len < 4 ) ? (__builtin_constant_p (value) && ((size_t)(const void *)((value) + 1) - (size_t)(const void *)(value) == 1) ? __builtin_strcmp (value, listener->ext_pickup) : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (value); int __result = (((const unsigned char *) (const char *) (listener->ext_pickup))[0] - __s2[0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (listener->ext_pickup))[1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (listener->ext_pickup))[2 ] - __s2[2]); if (__s2_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (listener->ext_pickup ))[3] - __s2[3]); } } __result; })))) : __builtin_strcmp (value , listener->ext_pickup)))); })) { | |||
| 1188 | listener->ext_pickup = switch_core_strdup(profile->pool, value)switch_core_perform_strdup(profile->pool, value, "skinny_server.c" , (const char *)__func__, 1188); | |||
| 1189 | } | |||
| 1190 | } else if (!strcasecmp(name, "ext-cfwdall")) { | |||
| 1191 | if (!listener->ext_cfwdall || strcmp(value,listener->ext_cfwdall)__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (value) && __builtin_constant_p (listener->ext_cfwdall ) && (__s1_len = __builtin_strlen (value), __s2_len = __builtin_strlen (listener->ext_cfwdall), (!((size_t)(const void *)((value) + 1) - (size_t)(const void *)(value) == 1) || __s1_len >= 4) && (!((size_t)(const void *)((listener ->ext_cfwdall) + 1) - (size_t)(const void *)(listener-> ext_cfwdall) == 1) || __s2_len >= 4)) ? __builtin_strcmp ( value, listener->ext_cfwdall) : (__builtin_constant_p (value ) && ((size_t)(const void *)((value) + 1) - (size_t)( const void *)(value) == 1) && (__s1_len = __builtin_strlen (value), __s1_len < 4) ? (__builtin_constant_p (listener-> ext_cfwdall) && ((size_t)(const void *)((listener-> ext_cfwdall) + 1) - (size_t)(const void *)(listener->ext_cfwdall ) == 1) ? __builtin_strcmp (value, listener->ext_cfwdall) : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (listener->ext_cfwdall); int __result = (((const unsigned char *) (const char *) (value))[0] - __s2 [0]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[1] - __s2 [1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[2] - __s2 [2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (value))[3] - __s2[ 3]); } } __result; }))) : (__builtin_constant_p (listener-> ext_cfwdall) && ((size_t)(const void *)((listener-> ext_cfwdall) + 1) - (size_t)(const void *)(listener->ext_cfwdall ) == 1) && (__s2_len = __builtin_strlen (listener-> ext_cfwdall), __s2_len < 4) ? (__builtin_constant_p (value ) && ((size_t)(const void *)((value) + 1) - (size_t)( const void *)(value) == 1) ? __builtin_strcmp (value, listener ->ext_cfwdall) : (- (__extension__ ({ const unsigned char * __s2 = (const unsigned char *) (const char *) (value); int __result = (((const unsigned char *) (const char *) (listener->ext_cfwdall ))[0] - __s2[0]); if (__s2_len > 0 && __result == 0 ) { __result = (((const unsigned char *) (const char *) (listener ->ext_cfwdall))[1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (listener->ext_cfwdall))[2] - __s2[2]); if (__s2_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (listener->ext_cfwdall))[3] - __s2 [3]); } } __result; })))) : __builtin_strcmp (value, listener ->ext_cfwdall)))); })) { | |||
| 1192 | listener->ext_cfwdall = switch_core_strdup(profile->pool, value)switch_core_perform_strdup(profile->pool, value, "skinny_server.c" , (const char *)__func__, 1192); | |||
| 1193 | } | |||
| 1194 | } else if (!strcasecmp(name, "ext-autodial")) { | |||
| 1195 | if (!listener->ext_autodial || strcmp(value,listener->ext_autodial)__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (value) && __builtin_constant_p (listener->ext_autodial ) && (__s1_len = __builtin_strlen (value), __s2_len = __builtin_strlen (listener->ext_autodial), (!((size_t)(const void *)((value) + 1) - (size_t)(const void *)(value) == 1) || __s1_len >= 4) && (!((size_t)(const void *)((listener ->ext_autodial) + 1) - (size_t)(const void *)(listener-> ext_autodial) == 1) || __s2_len >= 4)) ? __builtin_strcmp ( value, listener->ext_autodial) : (__builtin_constant_p (value ) && ((size_t)(const void *)((value) + 1) - (size_t)( const void *)(value) == 1) && (__s1_len = __builtin_strlen (value), __s1_len < 4) ? (__builtin_constant_p (listener-> ext_autodial) && ((size_t)(const void *)((listener-> ext_autodial) + 1) - (size_t)(const void *)(listener->ext_autodial ) == 1) ? __builtin_strcmp (value, listener->ext_autodial) : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (listener->ext_autodial); int __result = (((const unsigned char *) (const char *) (value))[0] - __s2 [0]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[1] - __s2 [1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (value))[2] - __s2 [2]); if (__s1_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (value))[3] - __s2[ 3]); } } __result; }))) : (__builtin_constant_p (listener-> ext_autodial) && ((size_t)(const void *)((listener-> ext_autodial) + 1) - (size_t)(const void *)(listener->ext_autodial ) == 1) && (__s2_len = __builtin_strlen (listener-> ext_autodial), __s2_len < 4) ? (__builtin_constant_p (value ) && ((size_t)(const void *)((value) + 1) - (size_t)( const void *)(value) == 1) ? __builtin_strcmp (value, listener ->ext_autodial) : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (value); int __result = (((const unsigned char *) (const char *) (listener->ext_autodial ))[0] - __s2[0]); if (__s2_len > 0 && __result == 0 ) { __result = (((const unsigned char *) (const char *) (listener ->ext_autodial))[1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (listener->ext_autodial))[2] - __s2[2]); if (__s2_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (listener->ext_autodial))[3] - __s2 [3]); } } __result; })))) : __builtin_strcmp (value, listener ->ext_autodial)))); })) { | |||
| 1196 | listener->ext_autodial = switch_core_strdup(profile->pool, value)switch_core_perform_strdup(profile->pool, value, "skinny_server.c" , (const char *)__func__, 1196); | |||
| 1197 | } | |||
| 1198 | } | |||
| 1199 | } | |||
| 1200 | } | |||
| 1201 | if ((xbuttons = switch_xml_child(xskinny, "buttons"))) { | |||
| 1202 | uint32_t line_instance = 1; | |||
| 1203 | char *network_ip = inet_ntoa(request->data.reg.ip); | |||
| 1204 | int network_port = 0; | |||
| 1205 | char network_port_c[6]; | |||
| 1206 | snprintf(network_port_c, sizeof(network_port_c), "%d", network_port); | |||
| 1207 | for (xbutton = switch_xml_child(xbuttons, "button"); xbutton; xbutton = xbutton->next) { | |||
| 1208 | uint32_t position = atoi(switch_xml_attr_soft(xbutton, "position")); | |||
| 1209 | uint32_t type = skinny_str2button(switch_xml_attr_soft(xbutton, "type")); | |||
| 1210 | const char *label = switch_xml_attr_soft(xbutton, "label"); | |||
| 1211 | const char *value = switch_xml_attr_soft(xbutton, "value"); | |||
| 1212 | if(type == SKINNY_BUTTON_LINE) { | |||
| 1213 | const char *caller_name = switch_xml_attr_soft(xbutton, "caller-name"); | |||
| 1214 | const char *reg_metadata = switch_xml_attr_soft(xbutton, "registration-metadata"); | |||
| 1215 | uint32_t ring_on_idle = 1; | |||
| 1216 | uint32_t ring_on_active = 1; | |||
| 1217 | uint32_t busy_trigger = atoi(switch_xml_attr_soft(xbutton, "busy-trigger")); | |||
| 1218 | const char *forward_all = switch_xml_attr_soft(xbutton, "forward-all"); | |||
| 1219 | const char *forward_busy = switch_xml_attr_soft(xbutton, "forward-busy"); | |||
| 1220 | const char *forward_noanswer = switch_xml_attr_soft(xbutton, "forward-noanswer"); | |||
| 1221 | uint32_t noanswer_duration = atoi(switch_xml_attr_soft(xbutton, "noanswer-duration")); | |||
| 1222 | const char *tmp; | |||
| 1223 | ||||
| 1224 | tmp = switch_xml_attr_soft(xbutton, "ring-on-active"); | |||
| 1225 | if ( !zstr(tmp)_zstr(tmp) ) { | |||
| 1226 | ring_on_active = atoi(tmp); | |||
| 1227 | } | |||
| 1228 | ||||
| 1229 | tmp = switch_xml_attr_soft(xbutton, "ring-on-idle"); | |||
| 1230 | if ( !zstr(tmp)_zstr(tmp) ) { | |||
| 1231 | ring_on_idle = atoi(tmp); | |||
| 1232 | } | |||
| 1233 | ||||
| 1234 | if ((sql = switch_mprintf( | |||
| 1235 | "INSERT INTO skinny_lines " | |||
| 1236 | "(device_name, device_instance, position, line_instance, " | |||
| 1237 | "label, value, caller_name, " | |||
| 1238 | "ring_on_idle, ring_on_active, busy_trigger, " | |||
| 1239 | "forward_all, forward_busy, forward_noanswer, noanswer_duration) " | |||
| 1240 | "VALUES('%q', %d, %d, %d, '%q', '%q', '%q', %d, %d, %d, '%q', '%q', '%q', %d)", | |||
| 1241 | request->data.reg.device_name, request->data.reg.instance, position, line_instance, | |||
| 1242 | label, value, caller_name, | |||
| 1243 | ring_on_idle, ring_on_active, busy_trigger, | |||
| 1244 | forward_all, forward_busy, forward_noanswer, noanswer_duration))) { | |||
| 1245 | char *token, *url; | |||
| 1246 | skinny_execute_sql(profile, sql, profile->sql_mutex); | |||
| 1247 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 1248 | token = switch_mprintf("skinny/%q/%q/%q:%d", profile->name, value, request->data.reg.device_name, request->data.reg.instance); | |||
| 1249 | url = switch_mprintf("skinny/%q/%q", profile->name, value); | |||
| 1250 | switch_core_add_registration(value, profile->domain, token, url, 0, network_ip, network_port_c, "tcp", reg_metadata); | |||
| 1251 | switch_safe_free(token)if (token) {free(token);token=((void*)0);}; | |||
| 1252 | switch_safe_free(url)if (url) {free(url);url=((void*)0);}; | |||
| 1253 | } | |||
| 1254 | if (line_instance == 1) { | |||
| 1255 | switch_event_t *message_query_event = NULL((void*)0); | |||
| 1256 | if (switch_event_create(&message_query_event, SWITCH_EVENT_MESSAGE_QUERY)switch_event_create_subclass_detailed("skinny_server.c", (const char * )(const char *)__func__, 1256, &message_query_event , SWITCH_EVENT_MESSAGE_QUERY, ((void*)0)) == SWITCH_STATUS_SUCCESS) { | |||
| 1257 | switch_event_add_header(message_query_event, SWITCH_STACK_BOTTOM, "Message-Account", "skinny:%s@%s", value, profile->domain); | |||
| 1258 | switch_event_add_header_string(message_query_event, SWITCH_STACK_BOTTOM, "VM-Skinny-Profile", profile->name); | |||
| 1259 | switch_event_fire(&message_query_event)switch_event_fire_detailed("skinny_server.c", (const char * ) (const char *)__func__, 1259, &message_query_event, ((void *)0)); | |||
| 1260 | } | |||
| 1261 | } | |||
| 1262 | line_instance++; | |||
| 1263 | } else { | |||
| 1264 | const char *settings = switch_xml_attr_soft(xbutton, "settings"); | |||
| 1265 | if ((sql = switch_mprintf( | |||
| 1266 | "INSERT INTO skinny_buttons " | |||
| 1267 | "(device_name, device_instance, position, type, label, value, settings) " | |||
| 1268 | "VALUES('%q', %d, %d, %d, '%q', '%q', '%q')", | |||
| 1269 | request->data.reg.device_name, | |||
| 1270 | request->data.reg.instance, | |||
| 1271 | position, | |||
| 1272 | type, | |||
| 1273 | label, | |||
| 1274 | value, | |||
| 1275 | settings))) { | |||
| 1276 | skinny_execute_sql(profile, sql, profile->sql_mutex); | |||
| 1277 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 1278 | } | |||
| 1279 | } | |||
| 1280 | } | |||
| 1281 | } | |||
| 1282 | } | |||
| 1283 | if (xroot) { | |||
| 1284 | switch_xml_free(xroot); | |||
| 1285 | } | |||
| 1286 | ||||
| 1287 | status = SWITCH_STATUS_SUCCESS; | |||
| 1288 | ||||
| 1289 | /* Reply with RegisterAckMessage */ | |||
| 1290 | send_register_ack(listener, profile->keep_alive, profile->date_format, "", profile->keep_alive, "")perform_send_register_ack(listener, "skinny_server.c", (const char *)__func__, 1290, profile->keep_alive, profile->date_format , "", profile->keep_alive, ""); | |||
| 1291 | ||||
| 1292 | /* Send CapabilitiesReqMessage */ | |||
| 1293 | send_capabilities_req(listener)perform_send_capabilities_req(listener, "skinny_server.c", (const char *)__func__, 1293); | |||
| 1294 | ||||
| 1295 | /* skinny::register event */ | |||
| 1296 | skinny_device_event(listener, &event, SWITCH_EVENT_CUSTOM, SKINNY_EVENT_REGISTER"skinny::register"); | |||
| 1297 | switch_event_fire(&event)switch_event_fire_detailed("skinny_server.c", (const char * ) (const char *)__func__, 1297, &event, ((void*)0)); | |||
| 1298 | ||||
| 1299 | keepalive_listener(listener, NULL((void*)0)); | |||
| 1300 | ||||
| 1301 | end: | |||
| 1302 | if(params) { | |||
| 1303 | switch_event_destroy(¶ms); | |||
| 1304 | } | |||
| 1305 | ||||
| 1306 | return status; | |||
| 1307 | } | |||
| 1308 | ||||
| 1309 | switch_status_t skinny_handle_port_message(listener_t *listener, skinny_message_t *request) | |||
| 1310 | { | |||
| 1311 | char *sql; | |||
| 1312 | skinny_profile_t *profile; | |||
| 1313 | ||||
| 1314 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 1314, __PRETTY_FUNCTION__)); | |||
| 1315 | switch_assert(listener->device_name)((listener->device_name) ? (void) (0) : __assert_fail ("listener->device_name" , "skinny_server.c", 1315, __PRETTY_FUNCTION__)); | |||
| 1316 | ||||
| 1317 | profile = listener->profile; | |||
| 1318 | ||||
| 1319 | skinny_check_data_length(request, sizeof(request->data.as_uint16))if (request->length < sizeof(request->data.as_uint16 )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 1319, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.as_uint16 )+4); return SWITCH_STATUS_FALSE; }; | |||
| 1320 | ||||
| 1321 | if ((sql = switch_mprintf( | |||
| 1322 | "UPDATE skinny_devices SET port=%d WHERE name='%q' and instance=%d", | |||
| 1323 | request->data.port.port, | |||
| 1324 | listener->device_name, | |||
| 1325 | listener->device_instance | |||
| 1326 | ))) { | |||
| 1327 | skinny_execute_sql(profile, sql, profile->sql_mutex); | |||
| 1328 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 1329 | } | |||
| 1330 | return SWITCH_STATUS_SUCCESS; | |||
| 1331 | } | |||
| 1332 | ||||
| 1333 | switch_status_t skinny_handle_keypad_button_message(listener_t *listener, skinny_message_t *request) | |||
| 1334 | { | |||
| 1335 | uint32_t line_instance = 1; | |||
| 1336 | uint32_t call_id = 0; | |||
| 1337 | switch_core_session_t *session = NULL((void*)0); | |||
| 1338 | ||||
| 1339 | skinny_check_data_length(request, sizeof(request->data.keypad_button.button))if (request->length < sizeof(request->data.keypad_button .button)+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 1339, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.keypad_button .button)+4); return SWITCH_STATUS_FALSE; }; | |||
| 1340 | ||||
| 1341 | if(skinny_check_data_length_soft(request, sizeof(request->data.keypad_button))(request->length >= sizeof(request->data.keypad_button )+4)) { | |||
| 1342 | if (request->data.keypad_button.line_instance > 0) { | |||
| 1343 | line_instance = request->data.keypad_button.line_instance; | |||
| 1344 | } | |||
| 1345 | call_id = request->data.keypad_button.call_id; | |||
| 1346 | } | |||
| 1347 | ||||
| 1348 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 1349 | if ( !session ) | |||
| 1350 | { | |||
| 1351 | line_instance = 0; | |||
| 1352 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, 0); | |||
| 1353 | } | |||
| 1354 | ||||
| 1355 | if(session) { | |||
| 1356 | switch_channel_t *channel = NULL((void*)0); | |||
| 1357 | private_t *tech_pvt = NULL((void*)0); | |||
| 1358 | char digit = '\0'; | |||
| 1359 | ||||
| 1360 | channel = switch_core_session_get_channel(session); | |||
| 1361 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 1362 | ||||
| 1363 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 1363, (const char*)(session), SWITCH_LOG_DEBUG, "SEND DTMF ON CALL %d [%d]\n", tech_pvt->call_id, request->data.keypad_button.button); | |||
| 1364 | ||||
| 1365 | if (request->data.keypad_button.button == 14) { | |||
| 1366 | digit = '*'; | |||
| 1367 | } else if (request->data.keypad_button.button == 15) { | |||
| 1368 | digit = '#'; | |||
| 1369 | } else if (request->data.keypad_button.button <= 9) { /* unsigned, so guaranteed to be >= 0 */ | |||
| 1370 | digit = '0' + request->data.keypad_button.button; | |||
| 1371 | } else { | |||
| 1372 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 1372, (const char*)(session), SWITCH_LOG_WARNING, "UNKNOW DTMF RECEIVED ON CALL %d [%d]\n", tech_pvt->call_id, request->data.keypad_button.button); | |||
| 1373 | } | |||
| 1374 | ||||
| 1375 | /* TODO check call_id and line */ | |||
| 1376 | ||||
| 1377 | if((skinny_line_get_state(listener, line_instance, tech_pvt->call_id) == SKINNY_OFF_HOOK)) { | |||
| 1378 | ||||
| 1379 | skinny_session_process_dest(session, listener, line_instance, NULL((void*)0), digit, 0); | |||
| 1380 | } else { | |||
| 1381 | if(digit != '\0') { | |||
| 1382 | switch_dtmf_t dtmf = { 0, switch_core_default_dtmf_duration(0)}; | |||
| 1383 | dtmf.digit = digit; | |||
| 1384 | switch_channel_queue_dtmf(channel, &dtmf); | |||
| 1385 | } | |||
| 1386 | } | |||
| 1387 | } | |||
| 1388 | ||||
| 1389 | if(session) { | |||
| 1390 | switch_core_session_rwunlock(session); | |||
| 1391 | } | |||
| 1392 | ||||
| 1393 | return SWITCH_STATUS_SUCCESS; | |||
| 1394 | } | |||
| 1395 | ||||
| 1396 | switch_status_t skinny_handle_enbloc_call_message(listener_t *listener, skinny_message_t *request) | |||
| 1397 | { | |||
| 1398 | uint32_t line_instance = 1; | |||
| 1399 | switch_core_session_t *session = NULL((void*)0); | |||
| 1400 | ||||
| 1401 | skinny_check_data_length(request, sizeof(request->data.enbloc_call.called_party))if (request->length < sizeof(request->data.enbloc_call .called_party)+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 1401, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.enbloc_call .called_party)+4); return SWITCH_STATUS_FALSE; }; | |||
| 1402 | ||||
| 1403 | if(skinny_check_data_length_soft(request, sizeof(request->data.enbloc_call))(request->length >= sizeof(request->data.enbloc_call )+4)) { | |||
| 1404 | if (request->data.enbloc_call.line_instance > 0) { | |||
| 1405 | line_instance = request->data.enbloc_call.line_instance; | |||
| 1406 | } | |||
| 1407 | } | |||
| 1408 | ||||
| 1409 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, 0); | |||
| 1410 | ||||
| 1411 | if(session) { | |||
| 1412 | skinny_session_process_dest(session, listener, line_instance, request->data.enbloc_call.called_party, '\0', 0); | |||
| 1413 | switch_core_session_rwunlock(session); | |||
| 1414 | } | |||
| 1415 | ||||
| 1416 | return SWITCH_STATUS_SUCCESS; | |||
| 1417 | } | |||
| 1418 | ||||
| 1419 | switch_status_t skinny_handle_stimulus_message(listener_t *listener, skinny_message_t *request) | |||
| 1420 | { | |||
| 1421 | switch_status_t status = SWITCH_STATUS_SUCCESS; | |||
| 1422 | uint32_t line_instance = 0; | |||
| 1423 | uint32_t call_id = 0; | |||
| 1424 | switch_core_session_t *session = NULL((void*)0); | |||
| 1425 | struct speed_dial_stat_res_message *button_speed_dial = NULL((void*)0); | |||
| 1426 | struct line_stat_res_message *button_line = NULL((void*)0); | |||
| 1427 | uint32_t line_state; | |||
| 1428 | ||||
| 1429 | switch_channel_t *channel = NULL((void*)0); | |||
| 1430 | ||||
| 1431 | skinny_check_data_length(request, sizeof(request->data.stimulus)-sizeof(request->data.stimulus.call_id))if (request->length < sizeof(request->data.stimulus) -sizeof(request->data.stimulus.call_id)+4) { switch_log_printf (SWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 1431, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.stimulus )-sizeof(request->data.stimulus.call_id)+4); return SWITCH_STATUS_FALSE ; }; | |||
| 1432 | ||||
| 1433 | if(skinny_check_data_length_soft(request, sizeof(request->data.stimulus))(request->length >= sizeof(request->data.stimulus)+4 )) { | |||
| 1434 | call_id = request->data.stimulus.call_id; | |||
| 1435 | } | |||
| 1436 | ||||
| 1437 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Received stimulus message of type (%s)\n",switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1438, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Received stimulus message of type (%s)\n", (_zstr(listener-> device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, skinny_button2str (request->data.stimulus.instance_type)) | |||
| 1438 | skinny_button2str(request->data.stimulus.instance_type))switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1438, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Received stimulus message of type (%s)\n", (_zstr(listener-> device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, skinny_button2str (request->data.stimulus.instance_type)); | |||
| 1439 | ||||
| 1440 | switch(request->data.stimulus.instance_type) { | |||
| 1441 | case SKINNY_BUTTON_LAST_NUMBER_REDIAL: | |||
| 1442 | skinny_create_incoming_session(listener, &line_instance, &session); | |||
| 1443 | if ( ! session ) { | |||
| 1444 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Unable to handle last number redial stimulus message, couldn't create incoming session.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1444, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Unable to handle last number redial stimulus message, couldn't create incoming session.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 1445 | return SWITCH_STATUS_FALSE; | |||
| 1446 | } | |||
| 1447 | skinny_session_process_dest(session, listener, line_instance, | |||
| 1448 | empty_null2(listener->ext_redial,listener->profile->ext_redial)((listener->ext_redial)?(listener->ext_redial):((listener ->profile->ext_redial)?(listener->profile->ext_redial ):((void*)0))), '\0', 0); | |||
| 1449 | break; | |||
| 1450 | case SKINNY_BUTTON_SPEED_DIAL: | |||
| 1451 | skinny_speed_dial_get(listener, request->data.stimulus.instance, &button_speed_dial); | |||
| 1452 | ||||
| 1453 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, 0); | |||
| 1454 | if(strlen(button_speed_dial->line) > 0) { | |||
| 1455 | if ( !session ) { | |||
| 1456 | skinny_create_incoming_session(listener, &line_instance, &session); | |||
| 1457 | } | |||
| 1458 | if ( !session ) { | |||
| 1459 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Unable to handle speed dial stimulus message, couldn't create incoming session.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1459, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Unable to handle speed dial stimulus message, couldn't create incoming session.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 1460 | return SWITCH_STATUS_FALSE; | |||
| 1461 | } | |||
| 1462 | skinny_session_process_dest(session, listener, line_instance, button_speed_dial->line, '\0', 0); | |||
| 1463 | } | |||
| 1464 | break; | |||
| 1465 | case SKINNY_BUTTON_HOLD: | |||
| 1466 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 1467 | ||||
| 1468 | if(session) { | |||
| 1469 | status = skinny_session_hold_line(session, listener, line_instance); | |||
| 1470 | } | |||
| 1471 | break; | |||
| 1472 | case SKINNY_BUTTON_TRANSFER: | |||
| 1473 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 1474 | ||||
| 1475 | if(session) { | |||
| 1476 | status = skinny_session_transfer(session, listener, line_instance); | |||
| 1477 | } | |||
| 1478 | break; | |||
| 1479 | case SKINNY_BUTTON_VOICEMAIL: | |||
| 1480 | skinny_create_incoming_session(listener, &line_instance, &session); | |||
| 1481 | if ( ! session ) { | |||
| 1482 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Unable to handle stimulus message, couldn't create incoming session.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1482, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Unable to handle stimulus message, couldn't create incoming session.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 1483 | return SWITCH_STATUS_FALSE; | |||
| 1484 | } | |||
| 1485 | skinny_session_process_dest(session, listener, line_instance, | |||
| 1486 | empty_null2(listener->ext_voicemail, listener->profile->ext_voicemail)((listener->ext_voicemail)?(listener->ext_voicemail):(( listener->profile->ext_voicemail)?(listener->profile ->ext_voicemail):((void*)0))), '\0', 0); | |||
| 1487 | break; | |||
| 1488 | ||||
| 1489 | case SKINNY_BUTTON_LINE: | |||
| 1490 | // Get the button data | |||
| 1491 | skinny_line_get(listener, request->data.stimulus.instance, &button_line); | |||
| 1492 | ||||
| 1493 | // Set the button and try to open the incoming session with this | |||
| 1494 | line_instance = button_line->number; | |||
| 1495 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 1496 | ||||
| 1497 | // If session and line match, answer the call | |||
| 1498 | if ( session && line_instance == button_line->number ) { | |||
| 1499 | line_state = skinny_line_get_state(listener, line_instance, call_id); | |||
| 1500 | ||||
| 1501 | if(line_state == SKINNY_OFF_HOOK) { | |||
| 1502 | channel = switch_core_session_get_channel(session); | |||
| 1503 | if (switch_channel_test_flag(channel, CF_HOLD)) { | |||
| 1504 | switch_ivr_unhold(session); | |||
| 1505 | } | |||
| 1506 | ||||
| 1507 | switch_channel_hangup(channel, SWITCH_CAUSE_NORMAL_CLEARING)switch_channel_perform_hangup(channel, "skinny_server.c", (const char *)__func__, 1507, SWITCH_CAUSE_NORMAL_CLEARING); | |||
| 1508 | } | |||
| 1509 | else { | |||
| 1510 | status = skinny_session_answer(session, listener, line_instance); | |||
| 1511 | } | |||
| 1512 | } | |||
| 1513 | else { | |||
| 1514 | if(skinny_check_data_length_soft(request, sizeof(request->data.soft_key_event))(request->length >= sizeof(request->data.soft_key_event )+4)) { | |||
| 1515 | line_instance = request->data.soft_key_event.line_instance; | |||
| 1516 | } | |||
| 1517 | ||||
| 1518 | skinny_create_incoming_session(listener, &line_instance, &session); | |||
| 1519 | if ( ! session ) { | |||
| 1520 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Unable to handle stimulus message, couldn't create incoming session.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1520, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Unable to handle stimulus message, couldn't create incoming session.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 1521 | return SWITCH_STATUS_FALSE; | |||
| 1522 | } | |||
| 1523 | skinny_session_process_dest(session, listener, line_instance, NULL((void*)0), '\0', 0); | |||
| 1524 | } | |||
| 1525 | break; | |||
| 1526 | ||||
| 1527 | default: | |||
| 1528 | switch_log_printf(SWITCH_CHANNEL_LOGSWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 1528, ((void*)0), SWITCH_LOG_WARNING, "Unknown Stimulus Type Received [%d]\n", request->data.stimulus.instance_type); | |||
| 1529 | } | |||
| 1530 | ||||
| 1531 | if(session) { | |||
| 1532 | switch_core_session_rwunlock(session); | |||
| 1533 | } | |||
| 1534 | ||||
| 1535 | return status; | |||
| 1536 | } | |||
| 1537 | ||||
| 1538 | switch_status_t skinny_handle_off_hook_message(listener_t *listener, skinny_message_t *request) | |||
| 1539 | { | |||
| 1540 | uint32_t line_instance = 1; | |||
| 1541 | uint32_t call_id = 0; | |||
| 1542 | switch_core_session_t *session = NULL((void*)0); | |||
| 1543 | private_t *tech_pvt = NULL((void*)0); | |||
| 1544 | uint32_t line_state; | |||
| 1545 | ||||
| 1546 | if(skinny_check_data_length_soft(request, sizeof(request->data.off_hook))(request->length >= sizeof(request->data.off_hook)+4 )) { | |||
| 1547 | if (request->data.off_hook.line_instance > 0) { | |||
| 1548 | line_instance = request->data.off_hook.line_instance; | |||
| 1549 | } | |||
| 1550 | call_id = request->data.off_hook.call_id; | |||
| 1551 | } | |||
| 1552 | ||||
| 1553 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 1554 | ||||
| 1555 | line_state = skinny_line_get_state(listener, line_instance, call_id); | |||
| 1556 | ||||
| 1557 | if(session && line_state == SKINNY_RING_IN ) { /*answering a call */ | |||
| 1558 | skinny_session_answer(session, listener, line_instance); | |||
| 1559 | } else { /* start a new call */ | |||
| 1560 | skinny_create_incoming_session(listener, &line_instance, &session); | |||
| 1561 | if ( ! session ) { | |||
| 1562 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Unable to handle off hook message, could not create session.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1562, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Unable to handle off hook message, could not create session.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 1563 | return SWITCH_STATUS_FALSE; | |||
| 1564 | } | |||
| 1565 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 1566 | assert(tech_pvt != NULL)((tech_pvt != ((void*)0)) ? (void) (0) : __assert_fail ("tech_pvt != ((void*)0)" , "skinny_server.c", 1566, __PRETTY_FUNCTION__)); | |||
| 1567 | ||||
| 1568 | skinny_session_process_dest(session, listener, line_instance, NULL((void*)0), '\0', 0); | |||
| 1569 | } | |||
| 1570 | ||||
| 1571 | if(session) { | |||
| 1572 | switch_core_session_rwunlock(session); | |||
| 1573 | } | |||
| 1574 | ||||
| 1575 | return SWITCH_STATUS_SUCCESS; | |||
| 1576 | } | |||
| 1577 | ||||
| 1578 | switch_status_t skinny_handle_on_hook_message(listener_t *listener, skinny_message_t *request) | |||
| 1579 | { | |||
| 1580 | switch_status_t status = SWITCH_STATUS_SUCCESS; | |||
| 1581 | uint32_t line_instance = 0; | |||
| 1582 | uint32_t call_id = 0; | |||
| 1583 | switch_core_session_t *session = NULL((void*)0); | |||
| 1584 | ||||
| 1585 | if(skinny_check_data_length_soft(request, sizeof(request->data.on_hook))(request->length >= sizeof(request->data.on_hook)+4)) { | |||
| 1586 | line_instance = request->data.on_hook.line_instance; | |||
| 1587 | call_id = request->data.on_hook.call_id; | |||
| 1588 | } | |||
| 1589 | ||||
| 1590 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 1591 | ||||
| 1592 | if(session) { | |||
| 1593 | switch_channel_t *channel = NULL((void*)0); | |||
| 1594 | private_t *tech_pvt = NULL((void*)0); | |||
| 1595 | ||||
| 1596 | channel = switch_core_session_get_channel(session); | |||
| 1597 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 1598 | ||||
| 1599 | if (tech_pvt->transfer_from_call_id) { /* blind transfer */ | |||
| 1600 | status = skinny_session_transfer(session, listener, line_instance); | |||
| 1601 | } else { | |||
| 1602 | if (skinny_line_get_state(listener, line_instance, call_id) != SKINNY_IN_USE_REMOTELY) { | |||
| 1603 | switch_channel_hangup(channel, SWITCH_CAUSE_NORMAL_CLEARING)switch_channel_perform_hangup(channel, "skinny_server.c", (const char *)__func__, 1603, SWITCH_CAUSE_NORMAL_CLEARING); | |||
| 1604 | } | |||
| 1605 | } | |||
| 1606 | } | |||
| 1607 | ||||
| 1608 | if(session) { | |||
| 1609 | switch_core_session_rwunlock(session); | |||
| 1610 | } | |||
| 1611 | ||||
| 1612 | return status; | |||
| 1613 | } | |||
| 1614 | switch_status_t skinny_handle_forward_stat_req_message(listener_t *listener, skinny_message_t *request) | |||
| 1615 | { | |||
| 1616 | skinny_message_t *message; | |||
| 1617 | ||||
| 1618 | skinny_check_data_length(request, sizeof(request->data.forward_stat_req))if (request->length < sizeof(request->data.forward_stat_req )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 1618, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.forward_stat_req )+4); return SWITCH_STATUS_FALSE; }; | |||
| 1619 | ||||
| 1620 | skinny_create_message(message, FORWARD_STAT_MESSAGE, forward_stat)message = calloc(1, 12 + sizeof(message->data.forward_stat )); message->type = 0x0090; message->length = 4 + sizeof (message->data.forward_stat); | |||
| 1621 | ||||
| 1622 | message->data.forward_stat.line_instance = request->data.forward_stat_req.line_instance; | |||
| 1623 | ||||
| 1624 | if ( listener->profile->debug >= 9 ) { | |||
| 1625 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Handle Forward Stat Req Message with Line Instance (%d)\n",switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1626, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Handle Forward Stat Req Message with Line Instance (%d)\n", (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, request->data.forward_stat_req.line_instance) | |||
| 1626 | request->data.forward_stat_req.line_instance)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1626, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Handle Forward Stat Req Message with Line Instance (%d)\n", (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, request->data.forward_stat_req.line_instance); | |||
| 1627 | } | |||
| 1628 | skinny_send_reply_quiet(listener, message, SWITCH_TRUE)skinny_perform_send_reply_quiet(listener, "skinny_server.c", ( const char *)__func__, 1628, message, SWITCH_TRUE); | |||
| 1629 | ||||
| 1630 | return SWITCH_STATUS_SUCCESS; | |||
| 1631 | } | |||
| 1632 | ||||
| 1633 | switch_status_t skinny_handle_speed_dial_stat_request(listener_t *listener, skinny_message_t *request) | |||
| 1634 | { | |||
| 1635 | struct speed_dial_stat_res_message *button = NULL((void*)0); | |||
| 1636 | ||||
| 1637 | skinny_check_data_length(request, sizeof(request->data.speed_dial_req))if (request->length < sizeof(request->data.speed_dial_req )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 1637, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.speed_dial_req )+4); return SWITCH_STATUS_FALSE; }; | |||
| 1638 | ||||
| 1639 | if ( listener->profile->debug >= 9 ) { | |||
| 1640 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Handle Speed Dial Stat Request for Number (%d)\n", request->data.speed_dial_req.number)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1640, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Handle Speed Dial Stat Request for Number (%d)\n", (_zstr(listener ->device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, request ->data.speed_dial_req.number); | |||
| 1641 | } | |||
| 1642 | ||||
| 1643 | skinny_speed_dial_get(listener, request->data.speed_dial_req.number, &button); | |||
| 1644 | ||||
| 1645 | send_speed_dial_stat_res(listener, request->data.speed_dial_req.number, button->line, button->label)perform_send_speed_dial_stat_res(listener, "skinny_server.c", (const char *)__func__, 1645, request->data.speed_dial_req .number, button->line, button->label); | |||
| 1646 | ||||
| 1647 | return SWITCH_STATUS_SUCCESS; | |||
| 1648 | } | |||
| 1649 | ||||
| 1650 | switch_status_t skinny_handle_line_stat_request(listener_t *listener, skinny_message_t *request) | |||
| 1651 | { | |||
| 1652 | skinny_message_t *message; | |||
| 1653 | struct line_stat_res_message *button = NULL((void*)0); | |||
| 1654 | ||||
| 1655 | skinny_check_data_length(request, sizeof(request->data.line_req))if (request->length < sizeof(request->data.line_req) +4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 1655, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.line_req )+4); return SWITCH_STATUS_FALSE; }; | |||
| 1656 | ||||
| 1657 | skinny_create_message(message, LINE_STAT_RES_MESSAGE, line_res)message = calloc(1, 12 + sizeof(message->data.line_res)); message ->type = 0x0092; message->length = 4 + sizeof(message-> data.line_res); | |||
| 1658 | ||||
| 1659 | skinny_line_get(listener, request->data.line_req.number, &button); | |||
| 1660 | ||||
| 1661 | memcpy(&message->data.line_res, button, sizeof(struct line_stat_res_message)); | |||
| 1662 | ||||
| 1663 | skinny_send_reply(listener, message, SWITCH_TRUE)skinny_perform_send_reply(listener, "skinny_server.c", (const char *)__func__, 1663, message, SWITCH_TRUE); | |||
| 1664 | ||||
| 1665 | return SWITCH_STATUS_SUCCESS; | |||
| 1666 | } | |||
| 1667 | ||||
| 1668 | int skinny_config_stat_res_callback(void *pArg, int argc, char **argv, char **columnNames) | |||
| 1669 | { | |||
| 1670 | skinny_message_t *message = pArg; | |||
| 1671 | char *device_name = argv[0]; | |||
| 1672 | int user_id = atoi(argv[1]); | |||
| 1673 | int instance = atoi(argv[2]); | |||
| 1674 | char *user_name = argv[3]; | |||
| 1675 | char *server_name = argv[4]; | |||
| 1676 | int number_lines = atoi(argv[5]); | |||
| 1677 | int number_speed_dials = atoi(argv[6]); | |||
| 1678 | ||||
| 1679 | switch_copy_string(message->data.config_res.device_name, device_name, 16); | |||
| 1680 | message->data.config_res.user_id = user_id; | |||
| 1681 | message->data.config_res.instance = instance; | |||
| 1682 | switch_copy_string(message->data.config_res.user_name, user_name, 40); | |||
| 1683 | switch_copy_string(message->data.config_res.server_name, server_name, 40); | |||
| 1684 | message->data.config_res.number_lines = number_lines; | |||
| 1685 | message->data.config_res.number_speed_dials = number_speed_dials; | |||
| 1686 | ||||
| 1687 | return 0; | |||
| 1688 | } | |||
| 1689 | ||||
| 1690 | switch_status_t skinny_handle_config_stat_request(listener_t *listener, skinny_message_t *request) | |||
| 1691 | { | |||
| 1692 | char *sql; | |||
| 1693 | skinny_message_t *message; | |||
| 1694 | skinny_profile_t *profile; | |||
| 1695 | ||||
| 1696 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 1696, __PRETTY_FUNCTION__)); | |||
| 1697 | switch_assert(listener->device_name)((listener->device_name) ? (void) (0) : __assert_fail ("listener->device_name" , "skinny_server.c", 1697, __PRETTY_FUNCTION__)); | |||
| 1698 | ||||
| 1699 | profile = listener->profile; | |||
| 1700 | ||||
| 1701 | skinny_create_message(message, CONFIG_STAT_RES_MESSAGE, config_res)message = calloc(1, 12 + sizeof(message->data.config_res)) ; message->type = 0x0093; message->length = 4 + sizeof( message->data.config_res); | |||
| 1702 | ||||
| 1703 | if ((sql = switch_mprintf( | |||
| 1704 | "SELECT name, user_id, instance, '' AS user_name, '' AS server_name, " | |||
| 1705 | "(SELECT COUNT(*) FROM skinny_lines WHERE device_name='%s' AND device_instance=%d) AS number_lines, " | |||
| 1706 | "(SELECT COUNT(*) FROM skinny_buttons WHERE device_name='%s' AND device_instance=%d AND type=%d) AS number_speed_dials " | |||
| 1707 | "FROM skinny_devices WHERE name='%s' ", | |||
| 1708 | listener->device_name, | |||
| 1709 | listener->device_instance, | |||
| 1710 | listener->device_name, | |||
| 1711 | listener->device_instance, | |||
| 1712 | SKINNY_BUTTON_SPEED_DIAL, | |||
| 1713 | listener->device_name | |||
| 1714 | ))) { | |||
| 1715 | skinny_execute_sql_callback(profile, profile->sql_mutex, sql, skinny_config_stat_res_callback, message); | |||
| 1716 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 1717 | } | |||
| 1718 | skinny_send_reply(listener, message, SWITCH_TRUE)skinny_perform_send_reply(listener, "skinny_server.c", (const char *)__func__, 1718, message, SWITCH_TRUE); | |||
| 1719 | ||||
| 1720 | return SWITCH_STATUS_SUCCESS; | |||
| 1721 | } | |||
| 1722 | ||||
| 1723 | switch_status_t skinny_handle_time_date_request(listener_t *listener, skinny_message_t *request) | |||
| 1724 | { | |||
| 1725 | return send_define_current_time_date(listener)perform_send_define_current_time_date(listener, "skinny_server.c" , (const char *)__func__, 1725); | |||
| 1726 | } | |||
| 1727 | ||||
| 1728 | struct button_template_helper { | |||
| 1729 | skinny_message_t *message; | |||
| 1730 | int count[SKINNY_BUTTON_UNDEFINED+1]; | |||
| 1731 | int max_position; | |||
| 1732 | }; | |||
| 1733 | ||||
| 1734 | int skinny_handle_button_template_request_callback(void *pArg, int argc, char **argv, char **columnNames) | |||
| 1735 | { | |||
| 1736 | struct button_template_helper *helper = pArg; | |||
| 1737 | skinny_message_t *message = helper->message; | |||
| 1738 | /* char *device_name = argv[0]; */ | |||
| 1739 | /* uint32_t device_instance = argv[1]; */ | |||
| 1740 | int position = atoi(argv[2]); | |||
| 1741 | uint32_t type = atoi(argv[3]); | |||
| 1742 | /* int relative_position = atoi(argv[4]); */ | |||
| 1743 | ||||
| 1744 | message->data.button_template.btn[position-1].instance_number = ++helper->count[type]; | |||
| 1745 | message->data.button_template.btn[position-1].button_definition = type; | |||
| 1746 | ||||
| 1747 | message->data.button_template.button_count++; | |||
| 1748 | message->data.button_template.total_button_count++; | |||
| 1749 | if(position > helper->max_position) { | |||
| 1750 | helper->max_position = position; | |||
| 1751 | } | |||
| 1752 | ||||
| 1753 | return 0; | |||
| 1754 | } | |||
| 1755 | ||||
| 1756 | switch_status_t skinny_handle_button_template_request(listener_t *listener, skinny_message_t *request) | |||
| 1757 | { | |||
| 1758 | skinny_message_t *message; | |||
| 1759 | struct button_template_helper helper = {0}; | |||
| 1760 | skinny_profile_t *profile; | |||
| 1761 | char *sql; | |||
| 1762 | int i; | |||
| 1763 | ||||
| 1764 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 1764, __PRETTY_FUNCTION__)); | |||
| 1765 | switch_assert(listener->device_name)((listener->device_name) ? (void) (0) : __assert_fail ("listener->device_name" , "skinny_server.c", 1765, __PRETTY_FUNCTION__)); | |||
| 1766 | ||||
| 1767 | profile = listener->profile; | |||
| 1768 | ||||
| 1769 | skinny_create_message(message, BUTTON_TEMPLATE_RES_MESSAGE, button_template)message = calloc(1, 12 + sizeof(message->data.button_template )); message->type = 0x0097; message->length = 4 + sizeof (message->data.button_template); | |||
| 1770 | ||||
| 1771 | message->data.button_template.button_offset = 0; | |||
| 1772 | message->data.button_template.button_count = 0; | |||
| 1773 | message->data.button_template.total_button_count = 0; | |||
| 1774 | ||||
| 1775 | helper.message = message; | |||
| 1776 | ||||
| 1777 | /* Add buttons */ | |||
| 1778 | if ((sql = switch_mprintf( | |||
| 1779 | "SELECT device_name, device_instance, position, type " | |||
| 1780 | "FROM skinny_buttons " | |||
| 1781 | "WHERE device_name='%s' AND device_instance=%d " | |||
| 1782 | "ORDER BY position", | |||
| 1783 | listener->device_name, listener->device_instance | |||
| 1784 | ))) { | |||
| 1785 | skinny_execute_sql_callback(profile, profile->sql_mutex, sql, skinny_handle_button_template_request_callback, &helper); | |||
| 1786 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 1787 | } | |||
| 1788 | ||||
| 1789 | /* Add lines */ | |||
| 1790 | if ((sql = switch_mprintf( | |||
| 1791 | "SELECT device_name, device_instance, position, %d AS type " | |||
| 1792 | "FROM skinny_lines " | |||
| 1793 | "WHERE device_name='%s' AND device_instance=%d " | |||
| 1794 | "ORDER BY position", | |||
| 1795 | SKINNY_BUTTON_LINE, | |||
| 1796 | listener->device_name, listener->device_instance | |||
| 1797 | ))) { | |||
| 1798 | skinny_execute_sql_callback(profile, profile->sql_mutex, sql, skinny_handle_button_template_request_callback, &helper); | |||
| 1799 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 1800 | } | |||
| 1801 | ||||
| 1802 | /* Fill remaining buttons with Undefined */ | |||
| 1803 | for(i = 0; i+1 < helper.max_position; i++) { | |||
| 1804 | if(message->data.button_template.btn[i].button_definition == SKINNY_BUTTON_UNKNOWN) { | |||
| 1805 | message->data.button_template.btn[i].instance_number = ++helper.count[SKINNY_BUTTON_UNDEFINED]; | |||
| 1806 | message->data.button_template.btn[i].button_definition = SKINNY_BUTTON_UNDEFINED; | |||
| 1807 | message->data.button_template.button_count++; | |||
| 1808 | message->data.button_template.total_button_count++; | |||
| 1809 | } | |||
| 1810 | } | |||
| 1811 | ||||
| 1812 | return skinny_send_reply(listener, message, SWITCH_TRUE)skinny_perform_send_reply(listener, "skinny_server.c", (const char *)__func__, 1812, message, SWITCH_TRUE); | |||
| 1813 | } | |||
| 1814 | ||||
| 1815 | switch_status_t skinny_handle_version_request(listener_t *listener, skinny_message_t *request) | |||
| 1816 | { | |||
| 1817 | int saw_entry = 0; | |||
| 1818 | ||||
| 1819 | if (zstr(listener->firmware_version)_zstr(listener->firmware_version)) { | |||
| 1820 | char *id_str; | |||
| 1821 | skinny_device_type_params_t *params; | |||
| 1822 | id_str = switch_mprintf("%d", listener->device_type); | |||
| 1823 | params = (skinny_device_type_params_t *) switch_core_hash_find(listener->profile->device_type_params_hash, id_str); | |||
| 1824 | if (params) { | |||
| 1825 | saw_entry = 1; | |||
| 1826 | ||||
| 1827 | if (!zstr(params->firmware_version)_zstr(params->firmware_version)) { | |||
| 1828 | switch_copy_string(listener->firmware_version, params->firmware_version, 16); | |||
| 1829 | } | |||
| 1830 | } | |||
| 1831 | } | |||
| 1832 | ||||
| 1833 | if (!zstr(listener->firmware_version)_zstr(listener->firmware_version)) { | |||
| 1834 | return send_version(listener, listener->firmware_version)perform_send_version(listener, "skinny_server.c", (const char *)__func__, 1834, listener->firmware_version); | |||
| 1835 | } else if (saw_entry) { | |||
| 1836 | /* found entry with an empty string */ | |||
| 1837 | return send_version(listener, "")perform_send_version(listener, "skinny_server.c", (const char *)__func__, 1837, ""); | |||
| 1838 | } else { | |||
| 1839 | switch_log_printf(SWITCH_CHANNEL_LOGSWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 1839, ((void*)0), SWITCH_LOG_WARNING, | |||
| 1840 | "Device %s:%d is requesting for firmware version, but none is set.\n", | |||
| 1841 | listener->device_name, listener->device_instance); | |||
| 1842 | ||||
| 1843 | /* CCM sends back an answer, but with all nulls */ | |||
| 1844 | return send_version(listener, "")perform_send_version(listener, "skinny_server.c", (const char *)__func__, 1844, ""); | |||
| 1845 | } | |||
| 1846 | } | |||
| 1847 | ||||
| 1848 | switch_status_t skinny_handle_capabilities_response(listener_t *listener, skinny_message_t *request) | |||
| 1849 | { | |||
| 1850 | char *sql; | |||
| 1851 | skinny_profile_t *profile; | |||
| 1852 | ||||
| 1853 | uint32_t i = 0; | |||
| 1854 | uint32_t n = 0; | |||
| 1855 | char *codec_order[SWITCH_MAX_CODECS50]; | |||
| 1856 | char *codec_string; | |||
| 1857 | ||||
| 1858 | size_t string_len, string_pos, pos; | |||
| 1859 | ||||
| 1860 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 1860, __PRETTY_FUNCTION__)); | |||
| 1861 | switch_assert(listener->device_name)((listener->device_name) ? (void) (0) : __assert_fail ("listener->device_name" , "skinny_server.c", 1861, __PRETTY_FUNCTION__)); | |||
| 1862 | ||||
| 1863 | profile = listener->profile; | |||
| 1864 | ||||
| 1865 | skinny_check_data_length(request, sizeof(request->data.cap_res.count))if (request->length < sizeof(request->data.cap_res.count )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 1865, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.cap_res .count)+4); return SWITCH_STATUS_FALSE; }; | |||
| 1866 | ||||
| 1867 | n = request->data.cap_res.count; | |||
| 1868 | if (n > SWITCH_MAX_CODECS50) { | |||
| 1869 | n = SWITCH_MAX_CODECS50; | |||
| 1870 | } | |||
| 1871 | string_len = -1; | |||
| 1872 | ||||
| 1873 | skinny_check_data_length(request, sizeof(request->data.cap_res.count) + n * sizeof(request->data.cap_res.caps[0]))if (request->length < sizeof(request->data.cap_res.count ) + n * sizeof(request->data.cap_res.caps[0])+4) { switch_log_printf (SWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 1873, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.cap_res .count) + n * sizeof(request->data.cap_res.caps[0])+4); return SWITCH_STATUS_FALSE; }; | |||
| 1874 | ||||
| 1875 | for (i = 0; i < n; i++) { | |||
| 1876 | char *codec = skinny_codec2string(request->data.cap_res.caps[i].codec); | |||
| 1877 | codec_order[i] = codec; | |||
| 1878 | string_len += strlen(codec)+1; | |||
| 1879 | } | |||
| 1880 | i = 0; | |||
| 1881 | pos = 0; | |||
| 1882 | ||||
| 1883 | if ( string_len > SKINNY_MAX_STRING16384 ) { | |||
| 1884 | skinny_log_l_msg(listener, SWITCH_LOG_ERROR, "Codec string list too long.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1884, ((void*)0), SWITCH_LOG_ERROR, "[%s:%d @ %s:%d] " "Codec string list too long.\n", (_zstr(listener->device_name ) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port); | |||
| 1885 | return SWITCH_STATUS_FALSE; | |||
| 1886 | } | |||
| 1887 | ||||
| 1888 | codec_string = calloc(string_len+1,1); | |||
| 1889 | if ( !codec_string ) { | |||
| 1890 | skinny_log_l_msg(listener, SWITCH_LOG_ERROR, "Unable to allocate memory for codec string.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1890, ((void*)0), SWITCH_LOG_ERROR, "[%s:%d @ %s:%d] " "Unable to allocate memory for codec string.\n", (_zstr(listener ->device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port); | |||
| 1891 | return SWITCH_STATUS_FALSE; | |||
| 1892 | } | |||
| 1893 | for (string_pos = 0; string_pos < string_len; string_pos++) { | |||
| 1894 | char *codec = codec_order[i]; | |||
| 1895 | switch_assert(i < n)((i < n) ? (void) (0) : __assert_fail ("i < n", "skinny_server.c" , 1895, __PRETTY_FUNCTION__)); | |||
| 1896 | if(pos == strlen(codec)) { | |||
| 1897 | codec_string[string_pos] = ','; | |||
| 1898 | i++; | |||
| 1899 | pos = 0; | |||
| 1900 | } else { | |||
| 1901 | codec_string[string_pos] = codec[pos++]; | |||
| 1902 | } | |||
| 1903 | } | |||
| 1904 | codec_string[string_len] = '\0'; | |||
| 1905 | if ((sql = switch_mprintf( | |||
| 1906 | "UPDATE skinny_devices SET codec_string='%q' WHERE name='%s'", | |||
| 1907 | codec_string, | |||
| 1908 | listener->device_name | |||
| 1909 | ))) { | |||
| 1910 | skinny_execute_sql(profile, sql, profile->sql_mutex); | |||
| 1911 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 1912 | } | |||
| 1913 | if ( listener->profile->debug >= 9 ) { | |||
| 1914 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Codecs %s supported.\n", codec_string)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1914, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Codecs %s supported.\n", (_zstr(listener->device_name) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port, codec_string); | |||
| 1915 | } | |||
| 1916 | switch_safe_free(codec_string)if (codec_string) {free(codec_string);codec_string=((void*)0) ;}; | |||
| 1917 | return SWITCH_STATUS_SUCCESS; | |||
| 1918 | } | |||
| 1919 | ||||
| 1920 | switch_status_t skinny_handle_alarm(listener_t *listener, skinny_message_t *request) | |||
| 1921 | { | |||
| 1922 | switch_event_t *event = NULL((void*)0); | |||
| 1923 | ||||
| 1924 | skinny_check_data_length(request, sizeof(request->data.alarm))if (request->length < sizeof(request->data.alarm)+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 1924, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.alarm) +4); return SWITCH_STATUS_FALSE; }; | |||
| 1925 | ||||
| 1926 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Received alarm: Severity=%d, DisplayMessage=%s, Param1=%d, Param2=%d.\n",switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1928, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Received alarm: Severity=%d, DisplayMessage=%s, Param1=%d, Param2=%d.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, request->data.alarm.alarm_severity, request-> data.alarm.display_message, request->data.alarm.alarm_param1 , request->data.alarm.alarm_param2) | |||
| 1927 | request->data.alarm.alarm_severity, request->data.alarm.display_message,switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1928, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Received alarm: Severity=%d, DisplayMessage=%s, Param1=%d, Param2=%d.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, request->data.alarm.alarm_severity, request-> data.alarm.display_message, request->data.alarm.alarm_param1 , request->data.alarm.alarm_param2) | |||
| 1928 | request->data.alarm.alarm_param1, request->data.alarm.alarm_param2)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 1928, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Received alarm: Severity=%d, DisplayMessage=%s, Param1=%d, Param2=%d.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, request->data.alarm.alarm_severity, request-> data.alarm.display_message, request->data.alarm.alarm_param1 , request->data.alarm.alarm_param2); | |||
| 1929 | ||||
| 1930 | /* skinny::alarm event */ | |||
| 1931 | skinny_device_event(listener, &event, SWITCH_EVENT_CUSTOM, SKINNY_EVENT_ALARM"skinny::alarm"); | |||
| 1932 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-Alarm-Severity", "%d", request->data.alarm.alarm_severity); | |||
| 1933 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-Alarm-DisplayMessage", "%s", request->data.alarm.display_message); | |||
| 1934 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-Alarm-Param1", "%d", request->data.alarm.alarm_param1); | |||
| 1935 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-Alarm-Param2", "%d", request->data.alarm.alarm_param2); | |||
| 1936 | switch_event_fire(&event)switch_event_fire_detailed("skinny_server.c", (const char * ) (const char *)__func__, 1936, &event, ((void*)0)); | |||
| 1937 | ||||
| 1938 | return SWITCH_STATUS_SUCCESS; | |||
| 1939 | } | |||
| 1940 | ||||
| 1941 | switch_status_t skinny_handle_open_receive_channel_ack_message(listener_t *listener, skinny_message_t *request) | |||
| 1942 | { | |||
| 1943 | switch_status_t status = SWITCH_STATUS_SUCCESS; | |||
| 1944 | uint32_t line_instance = 0; | |||
| 1945 | switch_core_session_t *session; | |||
| 1946 | ||||
| 1947 | skinny_check_data_length(request, sizeof(request->data.open_receive_channel_ack))if (request->length < sizeof(request->data.open_receive_channel_ack )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 1947, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.open_receive_channel_ack )+4); return SWITCH_STATUS_FALSE; }; | |||
| 1948 | ||||
| 1949 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, request->data.open_receive_channel_ack.pass_thru_party_id); | |||
| 1950 | ||||
| 1951 | if(session) { | |||
| 1952 | const char *err = NULL((void*)0); | |||
| 1953 | private_t *tech_pvt = NULL((void*)0); | |||
| 1954 | switch_channel_t *channel = NULL((void*)0); | |||
| 1955 | struct in_addr addr; | |||
| 1956 | switch_rtp_flag_t flags[SWITCH_RTP_FLAG_INVALID] = {0}; | |||
| 1957 | ||||
| 1958 | tech_pvt = switch_core_session_get_private(session)switch_core_session_get_private_class(session, SWITCH_PVT_PRIMARY ); | |||
| 1959 | channel = switch_core_session_get_channel(session); | |||
| 1960 | ||||
| 1961 | /* Codec */ | |||
| 1962 | tech_pvt->iananame = "PCMU"; /* TODO */ | |||
| 1963 | tech_pvt->codec_ms = SKINNY_PTIME20; /* TODO */ | |||
| 1964 | tech_pvt->rm_rate = 8000; /* TODO */ | |||
| 1965 | tech_pvt->rm_fmtp = NULL((void*)0); /* TODO */ | |||
| 1966 | tech_pvt->agreed_pt = (switch_payload_t) 0; /* TODO */ | |||
| 1967 | tech_pvt->rm_encoding = switch_core_strdup(switch_core_session_get_pool(session), "")switch_core_perform_strdup(switch_core_session_get_pool(session ), "", "skinny_server.c", (const char *)__func__, 1967); | |||
| 1968 | skinny_tech_set_codec(tech_pvt, 0); | |||
| 1969 | if ((status = skinny_tech_set_codec(tech_pvt, 0)) != SWITCH_STATUS_SUCCESS) { | |||
| 1970 | goto end; | |||
| 1971 | } | |||
| 1972 | ||||
| 1973 | tech_pvt->local_sdp_audio_ip = listener->local_ip; | |||
| 1974 | /* Request a local port from the core's allocator */ | |||
| 1975 | if (!(tech_pvt->local_sdp_audio_port = switch_rtp_request_port(tech_pvt->local_sdp_audio_ip))) { | |||
| 1976 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(tech_pvt->session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 1976, (const char*)(tech_pvt->session), SWITCH_LOG_CRIT, "No RTP ports available!\n"); | |||
| 1977 | return SWITCH_STATUS_FALSE; | |||
| 1978 | } | |||
| 1979 | ||||
| 1980 | tech_pvt->remote_sdp_audio_ip = inet_ntoa(request->data.open_receive_channel_ack.ip); | |||
| 1981 | tech_pvt->remote_sdp_audio_port = request->data.open_receive_channel_ack.port; | |||
| 1982 | ||||
| 1983 | tech_pvt->rtp_session = switch_rtp_new(tech_pvt->local_sdp_audio_ip, | |||
| 1984 | tech_pvt->local_sdp_audio_port, | |||
| 1985 | tech_pvt->remote_sdp_audio_ip, | |||
| 1986 | tech_pvt->remote_sdp_audio_port, | |||
| 1987 | tech_pvt->agreed_pt, | |||
| 1988 | tech_pvt->read_impl.samples_per_packet, | |||
| 1989 | tech_pvt->codec_ms * 1000, | |||
| 1990 | flags, "soft", &err, | |||
| 1991 | switch_core_session_get_pool(session)); | |||
| 1992 | switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(tech_pvt->session)SWITCH_CHANNEL_ID_SESSION, "skinny_server.c", (const char *)__func__ , 1992, (const char*)(tech_pvt->session), SWITCH_LOG_DEBUG, | |||
| 1993 | "AUDIO RTP [%s] %s:%d->%s:%d codec: %u ms: %d [%s]\n", | |||
| 1994 | switch_channel_get_name(channel), | |||
| 1995 | tech_pvt->local_sdp_audio_ip, | |||
| 1996 | tech_pvt->local_sdp_audio_port, | |||
| 1997 | tech_pvt->remote_sdp_audio_ip, | |||
| 1998 | tech_pvt->remote_sdp_audio_port, | |||
| 1999 | tech_pvt->agreed_pt, | |||
| 2000 | tech_pvt->read_impl.microseconds_per_packet / 1000, | |||
| 2001 | switch_rtp_ready(tech_pvt->rtp_session) ? "SUCCESS" : err); | |||
| 2002 | #ifdef WIN32 | |||
| 2003 | addr.s_addr = inet_addr(tech_pvt->local_sdp_audio_ip); | |||
| 2004 | #else | |||
| 2005 | inet_aton(tech_pvt->local_sdp_audio_ip, &addr); | |||
| 2006 | #endif | |||
| 2007 | send_start_media_transmission(listener,perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2008 | tech_pvt->call_id, /* uint32_t conference_id, */perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2009 | tech_pvt->party_id, /* uint32_t pass_thru_party_id, */perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2010 | addr.s_addr, /* uint32_t remote_ip, */perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2011 | tech_pvt->local_sdp_audio_port, /* uint32_t remote_port, */perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2012 | SKINNY_PTIME, /* uint32_t ms_per_packet, */perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2013 | SKINNY_CODEC_ULAW_64K, /* uint32_t payload_capacity, */perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2014 | 184, /* uint32_t precedence, */perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2015 | 0, /* uint32_t silence_suppression, */perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2016 | 0, /* uint16_t max_frames_per_packet, */perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2017 | 0 /* uint32_t g723_bitrate */perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0) | |||
| 2018 | )perform_send_start_media_transmission(listener,"skinny_server.c" , (const char *)__func__, 2018,tech_pvt->call_id, tech_pvt ->party_id, addr.s_addr, tech_pvt->local_sdp_audio_port , 20, SKINNY_CODEC_ULAW_64K, 184, 0, 0, 0); | |||
| 2019 | ||||
| 2020 | switch_set_flag_locked(tech_pvt, TFLAG_IO)((tech_pvt->flag_mutex != ((void*)0)) ? (void) (0) : __assert_fail ("tech_pvt->flag_mutex != ((void*)0)", "skinny_server.c", 2020, __PRETTY_FUNCTION__));switch_mutex_lock(tech_pvt->flag_mutex );(tech_pvt)->flags |= (TFLAG_IO);switch_mutex_unlock(tech_pvt ->flag_mutex);; | |||
| 2021 | if (switch_channel_direction(channel) == SWITCH_CALL_DIRECTION_OUTBOUND) { | |||
| 2022 | switch_channel_mark_answered(channel)switch_channel_perform_mark_answered(channel, "skinny_server.c" , (const char *)__func__, 2022); | |||
| 2023 | } | |||
| 2024 | if (switch_channel_test_flag(channel, CF_HOLD)) { | |||
| 2025 | switch_ivr_unhold(session); | |||
| 2026 | send_set_lamp(listener, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_ON)perform_send_set_lamp(listener, "skinny_server.c", (const char *)__func__, 2026, SKINNY_BUTTON_LINE, line_instance, SKINNY_LAMP_ON ); | |||
| 2027 | } | |||
| 2028 | } else { | |||
| 2029 | skinny_log_l(listener, SWITCH_LOG_WARNING, "Unable to find session for call id=%d.\n",switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2030, ((void*)0), SWITCH_LOG_WARNING, "[%s:%d @ %s:%d] " "Unable to find session for call id=%d.\n", (_zstr(listener-> device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, request ->data.open_receive_channel_ack.pass_thru_party_id) | |||
| 2030 | request->data.open_receive_channel_ack.pass_thru_party_id)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2030, ((void*)0), SWITCH_LOG_WARNING, "[%s:%d @ %s:%d] " "Unable to find session for call id=%d.\n", (_zstr(listener-> device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, request ->data.open_receive_channel_ack.pass_thru_party_id); | |||
| 2031 | } | |||
| 2032 | end: | |||
| 2033 | if(session) { | |||
| 2034 | switch_core_session_rwunlock(session); | |||
| 2035 | } | |||
| 2036 | return status; | |||
| 2037 | } | |||
| 2038 | ||||
| 2039 | switch_status_t skinny_handle_soft_key_set_request(listener_t *listener, skinny_message_t *request) | |||
| 2040 | { | |||
| 2041 | skinny_message_t *message = NULL((void*)0); | |||
| 2042 | ||||
| 2043 | if (listener->soft_key_set_set) { | |||
| 2044 | message = switch_core_hash_find(listener->profile->soft_key_set_sets_hash, listener->soft_key_set_set); | |||
| 2045 | if ( listener->profile->debug >= 9 ) { | |||
| 2046 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Handle Soft Key Set Request with Set (%s)\n", listener->soft_key_set_set)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2046, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Handle Soft Key Set Request with Set (%s)\n", (_zstr(listener ->device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, listener ->soft_key_set_set); | |||
| 2047 | } | |||
| 2048 | } | |||
| 2049 | if (!message) { | |||
| 2050 | message = switch_core_hash_find(listener->profile->soft_key_set_sets_hash, "default"); | |||
| 2051 | if ( listener->profile->debug >= 9 ) { | |||
| 2052 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Handle Soft Key Set Request with Set (%s)\n", "default")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2052, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Handle Soft Key Set Request with Set (%s)\n", (_zstr(listener ->device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, "default" ); | |||
| 2053 | } | |||
| 2054 | } | |||
| 2055 | if (message) { | |||
| 2056 | skinny_send_reply_quiet(listener, message, SWITCH_FALSE)skinny_perform_send_reply_quiet(listener, "skinny_server.c", ( const char *)__func__, 2056, message, SWITCH_FALSE); | |||
| 2057 | } else { | |||
| 2058 | skinny_log_l(listener, SWITCH_LOG_ERROR, "Profile %s doesn't have a default <soft-key-set-set>.\n",switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2059, ((void*)0), SWITCH_LOG_ERROR, "[%s:%d @ %s:%d] " "Profile %s doesn't have a default <soft-key-set-set>.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, listener->profile->name) | |||
| 2059 | listener->profile->name)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2059, ((void*)0), SWITCH_LOG_ERROR, "[%s:%d @ %s:%d] " "Profile %s doesn't have a default <soft-key-set-set>.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, listener->profile->name); | |||
| 2060 | } | |||
| 2061 | ||||
| 2062 | /* Init the states */ | |||
| 2063 | send_select_soft_keys(listener, 0, 0, SKINNY_KEY_SET_ON_HOOK, 0xffff)perform_send_select_soft_keys(listener, "skinny_server.c", (const char *)__func__, 2063, 0, 0, SKINNY_KEY_SET_ON_HOOK, 0xffff); | |||
| 2064 | ||||
| 2065 | return SWITCH_STATUS_SUCCESS; | |||
| 2066 | } | |||
| 2067 | ||||
| 2068 | switch_status_t skinny_handle_soft_key_event_message(listener_t *listener, skinny_message_t *request) | |||
| 2069 | { | |||
| 2070 | switch_status_t status = SWITCH_STATUS_SUCCESS; | |||
| 2071 | uint32_t line_instance = 0; | |||
| 2072 | uint32_t call_id = 0; | |||
| 2073 | switch_core_session_t *session = NULL((void*)0); | |||
| 2074 | switch_channel_t *channel = NULL((void*)0); | |||
| 2075 | ||||
| 2076 | skinny_check_data_length(request, sizeof(request->data.soft_key_event.event))if (request->length < sizeof(request->data.soft_key_event .event)+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 2076, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.soft_key_event .event)+4); return SWITCH_STATUS_FALSE; }; | |||
| 2077 | ||||
| 2078 | if(skinny_check_data_length_soft(request, sizeof(request->data.soft_key_event))(request->length >= sizeof(request->data.soft_key_event )+4)) { | |||
| 2079 | line_instance = request->data.soft_key_event.line_instance; | |||
| 2080 | call_id = request->data.soft_key_event.call_id; | |||
| 2081 | } | |||
| 2082 | ||||
| 2083 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Soft Key Event (%s) with Line Instance (%d), Call ID (%d)\n",switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2084, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Soft Key Event (%s) with Line Instance (%d), Call ID (%d)\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, skinny_soft_key_event2str(request->data.soft_key_event .event), line_instance, call_id) | |||
| 2084 | skinny_soft_key_event2str(request->data.soft_key_event.event), line_instance, call_id)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2084, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Soft Key Event (%s) with Line Instance (%d), Call ID (%d)\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, skinny_soft_key_event2str(request->data.soft_key_event .event), line_instance, call_id); | |||
| 2085 | ||||
| 2086 | switch(request->data.soft_key_event.event) { | |||
| 2087 | case SOFTKEY_REDIAL: | |||
| 2088 | status = skinny_create_incoming_session(listener, &line_instance, &session); | |||
| 2089 | if ( ! session ) { | |||
| 2090 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Unable to handle soft key event, could not create incoming session.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2090, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Unable to handle soft key event, could not create incoming session.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 2091 | return SWITCH_STATUS_FALSE; | |||
| 2092 | } | |||
| 2093 | skinny_session_process_dest(session, listener, line_instance, | |||
| 2094 | empty_null2(listener->ext_redial,listener->profile->ext_redial)((listener->ext_redial)?(listener->ext_redial):((listener ->profile->ext_redial)?(listener->profile->ext_redial ):((void*)0))), '\0', 0); | |||
| 2095 | break; | |||
| 2096 | case SOFTKEY_NEWCALL: | |||
| 2097 | status = skinny_create_incoming_session(listener, &line_instance, &session); | |||
| 2098 | if ( ! session ) { | |||
| 2099 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Unable to handle soft key event, could not create incoming session.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2099, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Unable to handle soft key event, could not create incoming session.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 2100 | return SWITCH_STATUS_FALSE; | |||
| 2101 | } | |||
| 2102 | skinny_session_process_dest(session, listener, line_instance, NULL((void*)0), '\0', 0); | |||
| 2103 | break; | |||
| 2104 | case SOFTKEY_HOLD: | |||
| 2105 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 2106 | if(session) { | |||
| 2107 | status = skinny_session_hold_line(session, listener, line_instance); | |||
| 2108 | } | |||
| 2109 | break; | |||
| 2110 | case SOFTKEY_TRANSFER: | |||
| 2111 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 2112 | ||||
| 2113 | if(session) { | |||
| 2114 | status = skinny_session_transfer(session, listener, line_instance); | |||
| 2115 | } | |||
| 2116 | break; | |||
| 2117 | case SOFTKEY_BACKSPACE: | |||
| 2118 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 2119 | if(session) { | |||
| 2120 | skinny_session_process_dest(session, listener, line_instance, NULL((void*)0), '\0', 1); | |||
| 2121 | } | |||
| 2122 | break; | |||
| 2123 | case SOFTKEY_ENDCALL: | |||
| 2124 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 2125 | if(session) { | |||
| 2126 | channel = switch_core_session_get_channel(session); | |||
| 2127 | if (switch_channel_test_flag(channel, CF_HOLD)) { | |||
| 2128 | switch_ivr_unhold(session); | |||
| 2129 | } | |||
| 2130 | switch_channel_hangup(channel, SWITCH_CAUSE_NORMAL_CLEARING)switch_channel_perform_hangup(channel, "skinny_server.c", (const char *)__func__, 2130, SWITCH_CAUSE_NORMAL_CLEARING); | |||
| 2131 | } | |||
| 2132 | break; | |||
| 2133 | case SOFTKEY_RESUME: | |||
| 2134 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 2135 | if(session) { | |||
| 2136 | status = skinny_session_unhold_line(session, listener, line_instance); | |||
| 2137 | } | |||
| 2138 | break; | |||
| 2139 | case SOFTKEY_ANSWER: | |||
| 2140 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 2141 | if(session) { | |||
| 2142 | status = skinny_session_answer(session, listener, line_instance); | |||
| 2143 | } | |||
| 2144 | break; | |||
| 2145 | case SOFTKEY_IDIVERT: | |||
| 2146 | session = skinny_profile_find_session(listener->profile, listener, &line_instance, call_id); | |||
| 2147 | if(session) { | |||
| 2148 | switch_channel_t *channel = NULL((void*)0); | |||
| 2149 | channel = switch_core_session_get_channel(session); | |||
| 2150 | ||||
| 2151 | if (channel) { | |||
| 2152 | switch_channel_hangup(channel, SWITCH_CAUSE_NO_ANSWER)switch_channel_perform_hangup(channel, "skinny_server.c", (const char *)__func__, 2152, SWITCH_CAUSE_NO_ANSWER); | |||
| 2153 | } | |||
| 2154 | } | |||
| 2155 | break; | |||
| 2156 | case SOFTKEY_MEETME: | |||
| 2157 | skinny_create_incoming_session(listener, &line_instance, &session); | |||
| 2158 | if ( ! session ) { | |||
| 2159 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Unable to handle soft key event, could not create incoming session.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2159, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Unable to handle soft key event, could not create incoming session.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 2160 | return SWITCH_STATUS_FALSE; | |||
| 2161 | } | |||
| 2162 | skinny_session_process_dest(session, listener, line_instance, | |||
| 2163 | empty_null2(listener->ext_meetme, listener->profile->ext_meetme)((listener->ext_meetme)?(listener->ext_meetme):((listener ->profile->ext_meetme)?(listener->profile->ext_meetme ):((void*)0))), '\0', 0); | |||
| 2164 | break; | |||
| 2165 | case SOFTKEY_CALLPICKUP: | |||
| 2166 | case SOFTKEY_GRPCALLPICKUP: | |||
| 2167 | skinny_create_incoming_session(listener, &line_instance, &session); | |||
| 2168 | if ( ! session ) { | |||
| 2169 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Unable to handle soft key event, could not create incoming session.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2169, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Unable to handle soft key event, could not create incoming session.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 2170 | return SWITCH_STATUS_FALSE; | |||
| 2171 | } | |||
| 2172 | skinny_session_process_dest(session, listener, line_instance, | |||
| 2173 | empty_null2(listener->ext_pickup, listener->profile->ext_pickup)((listener->ext_pickup)?(listener->ext_pickup):((listener ->profile->ext_pickup)?(listener->profile->ext_pickup ):((void*)0))), '\0', 0); | |||
| 2174 | break; | |||
| 2175 | case SOFTKEY_CFWDALL: | |||
| 2176 | skinny_create_incoming_session(listener, &line_instance, &session); | |||
| 2177 | if ( ! session ) { | |||
| 2178 | skinny_log_l_msg(listener, SWITCH_LOG_CRIT, "Unable to handle soft key event, could not create incoming session.\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2178, ((void*)0), SWITCH_LOG_CRIT, "[%s:%d @ %s:%d] " "Unable to handle soft key event, could not create incoming session.\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port); | |||
| 2179 | return SWITCH_STATUS_FALSE; | |||
| 2180 | } | |||
| 2181 | skinny_session_process_dest(session, listener, line_instance, | |||
| 2182 | empty_null2(listener->ext_cfwdall, listener->profile->ext_cfwdall)((listener->ext_cfwdall)?(listener->ext_cfwdall):((listener ->profile->ext_cfwdall)?(listener->profile->ext_cfwdall ):((void*)0))), '\0', 0); | |||
| 2183 | break; | |||
| 2184 | default: | |||
| 2185 | switch_log_printf(SWITCH_CHANNEL_LOGSWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 2185, ((void*)0), SWITCH_LOG_WARNING, | |||
| 2186 | "Unknown SoftKeyEvent type: %d.\n", request->data.soft_key_event.event); | |||
| 2187 | } | |||
| 2188 | ||||
| 2189 | if(session) { | |||
| 2190 | switch_core_session_rwunlock(session); | |||
| 2191 | } | |||
| 2192 | ||||
| 2193 | return status; | |||
| 2194 | } | |||
| 2195 | ||||
| 2196 | switch_status_t skinny_handle_unregister(listener_t *listener, skinny_message_t *request) | |||
| 2197 | { | |||
| 2198 | switch_event_t *event = NULL((void*)0); | |||
| 2199 | skinny_message_t *message; | |||
| 2200 | ||||
| 2201 | /* skinny::unregister event */ | |||
| 2202 | skinny_device_event(listener, &event, SWITCH_EVENT_CUSTOM, SKINNY_EVENT_UNREGISTER"skinny::unregister"); | |||
| 2203 | switch_event_fire(&event)switch_event_fire_detailed("skinny_server.c", (const char * ) (const char *)__func__, 2203, &event, ((void*)0)); | |||
| 2204 | ||||
| 2205 | skinny_create_message(message, UNREGISTER_ACK_MESSAGE, unregister_ack)message = calloc(1, 12 + sizeof(message->data.unregister_ack )); message->type = 0x0118; message->length = 4 + sizeof (message->data.unregister_ack); | |||
| 2206 | ||||
| 2207 | message->data.unregister_ack.unregister_status = 0; /* OK */ | |||
| 2208 | ||||
| 2209 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Handle Unregister with Status (%d)\n", message->data.unregister_ack.unregister_status)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2209, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Handle Unregister with Status (%d)\n", (_zstr(listener-> device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, message ->data.unregister_ack.unregister_status); | |||
| 2210 | ||||
| 2211 | skinny_send_reply_quiet(listener, message, SWITCH_TRUE)skinny_perform_send_reply_quiet(listener, "skinny_server.c", ( const char *)__func__, 2211, message, SWITCH_TRUE); | |||
| 2212 | ||||
| 2213 | /* Close socket */ | |||
| 2214 | switch_clear_flag_locked(listener, LFLAG_RUNNING)switch_mutex_lock(listener->flag_mutex); (listener)->flags &= ~(LFLAG_RUNNING); switch_mutex_unlock(listener->flag_mutex );; | |||
| 2215 | ||||
| 2216 | /* Clear this device from database and any active lines/etc. */ | |||
| 2217 | skinny_clean_listener_from_db(listener); | |||
| 2218 | ||||
| 2219 | return SWITCH_STATUS_SUCCESS; | |||
| 2220 | } | |||
| 2221 | ||||
| 2222 | switch_status_t skinny_handle_soft_key_template_request(listener_t *listener, skinny_message_t *request) | |||
| 2223 | { | |||
| 2224 | size_t i; | |||
| 2225 | skinny_message_t *message; | |||
| 2226 | ||||
| 2227 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 2227, __PRETTY_FUNCTION__)); | |||
| 2228 | switch_assert(listener->device_name)((listener->device_name) ? (void) (0) : __assert_fail ("listener->device_name" , "skinny_server.c", 2228, __PRETTY_FUNCTION__)); | |||
| 2229 | ||||
| 2230 | skinny_create_message(message, SOFT_KEY_TEMPLATE_RES_MESSAGE, soft_key_template)message = calloc(1, 12 + sizeof(message->data.soft_key_template )); message->type = 0x0108; message->length = 4 + sizeof (message->data.soft_key_template); | |||
| 2231 | ||||
| 2232 | message->data.soft_key_template.soft_key_offset = 0; | |||
| 2233 | message->data.soft_key_template.soft_key_count = 21; | |||
| 2234 | message->data.soft_key_template.total_soft_key_count = 21; | |||
| 2235 | ||||
| 2236 | for (i=0; i < sizeof(soft_key_template_default_textids)/4; i++) { | |||
| 2237 | char *label = skinny_textid2raw(soft_key_template_default_textids[i])(soft_key_template_default_textids[i] > 0 ? switch_mprintf ("\200%c", soft_key_template_default_textids[i]) : switch_mprintf ("")); | |||
| 2238 | switch_copy_string(message->data.soft_key_template.soft_key[i].soft_key_label, label, sizeof(message->data.soft_key_template.soft_key[i].soft_key_label)); | |||
| 2239 | switch_safe_free(label)if (label) {free(label);label=((void*)0);}; | |||
| 2240 | ||||
| 2241 | message->data.soft_key_template.soft_key[i].soft_key_event = soft_key_template_default_events[i]; | |||
| 2242 | } | |||
| 2243 | ||||
| 2244 | if ( listener->profile->debug >= 9 ) { | |||
| 2245 | skinny_log_l_msg(listener, SWITCH_LOG_DEBUG, "Handle Soft Key Template Request with Default Template\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2245, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Handle Soft Key Template Request with Default Template\n", ( _zstr(listener->device_name) ? "_undef_" : listener->device_name ), listener->device_instance, (_zstr(listener->remote_ip ) ? "_undef_" : listener->remote_ip), listener->remote_port ); | |||
| 2246 | } | |||
| 2247 | ||||
| 2248 | skinny_send_reply_quiet(listener, message, SWITCH_TRUE)skinny_perform_send_reply_quiet(listener, "skinny_server.c", ( const char *)__func__, 2248, message, SWITCH_TRUE); | |||
| 2249 | ||||
| 2250 | return SWITCH_STATUS_SUCCESS; | |||
| 2251 | } | |||
| 2252 | ||||
| 2253 | switch_status_t skinny_headset_status_message(listener_t *listener, skinny_message_t *request) | |||
| 2254 | { | |||
| 2255 | char *sql; | |||
| 2256 | ||||
| 2257 | skinny_check_data_length(request, sizeof(request->data.headset_status))if (request->length < sizeof(request->data.headset_status )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 2257, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.headset_status )+4); return SWITCH_STATUS_FALSE; }; | |||
| 2258 | ||||
| 2259 | if ((sql = switch_mprintf( | |||
| 2260 | "UPDATE skinny_devices SET headset=%d WHERE name='%q' and instance=%d", | |||
| 2261 | (request->data.headset_status.mode==1) ? SKINNY_ACCESSORY_STATE_OFFHOOK : SKINNY_ACCESSORY_STATE_ONHOOK, | |||
| 2262 | listener->device_name, | |||
| 2263 | listener->device_instance | |||
| 2264 | ))) { | |||
| 2265 | skinny_execute_sql(listener->profile, sql, listener->profile->sql_mutex); | |||
| 2266 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 2267 | } | |||
| 2268 | ||||
| 2269 | if ( listener->profile->debug >= 9 ) { | |||
| 2270 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Update headset accessory status (%s)\n",switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2271, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Update headset accessory status (%s)\n", (_zstr(listener-> device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, skinny_accessory_state2str (request->data.headset_status.mode)) | |||
| 2271 | skinny_accessory_state2str(request->data.headset_status.mode))switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2271, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Update headset accessory status (%s)\n", (_zstr(listener-> device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, skinny_accessory_state2str (request->data.headset_status.mode)); | |||
| 2272 | } | |||
| 2273 | ||||
| 2274 | return SWITCH_STATUS_SUCCESS; | |||
| 2275 | } | |||
| 2276 | ||||
| 2277 | switch_status_t skinny_handle_media_resource_message(listener_t *listener, skinny_message_t *request) | |||
| 2278 | { | |||
| 2279 | skinny_check_data_length(request, sizeof(request->data.media_resource))if (request->length < sizeof(request->data.media_resource )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 2279, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.media_resource )+4); return SWITCH_STATUS_FALSE; }; | |||
| 2280 | ||||
| 2281 | skinny_log_l_msg(listener, SWITCH_LOG_DEBUG, "Handle Media Resource Notification\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2281, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Handle Media Resource Notification\n", (_zstr(listener-> device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port); | |||
| 2282 | ||||
| 2283 | /* Do nothing */ | |||
| 2284 | return SWITCH_STATUS_SUCCESS; | |||
| 2285 | } | |||
| 2286 | ||||
| 2287 | switch_status_t skinny_handle_register_available_lines_message(listener_t *listener, skinny_message_t *request) | |||
| 2288 | { | |||
| 2289 | skinny_check_data_length(request, sizeof(request->data.reg_lines))if (request->length < sizeof(request->data.reg_lines )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 2289, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.reg_lines )+4); return SWITCH_STATUS_FALSE; }; | |||
| 2290 | ||||
| 2291 | if ( listener->profile->debug >= 9 ) { | |||
| 2292 | skinny_log_l_msg(listener, SWITCH_LOG_DEBUG, "Handle Register Available Lines\n")switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2292, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Handle Register Available Lines\n", (_zstr(listener->device_name ) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port); | |||
| 2293 | } | |||
| 2294 | ||||
| 2295 | /* Do nothing */ | |||
| 2296 | return SWITCH_STATUS_SUCCESS; | |||
| 2297 | } | |||
| 2298 | ||||
| 2299 | switch_status_t skinny_handle_data_message(listener_t *listener, skinny_message_t *request) | |||
| 2300 | { | |||
| 2301 | switch_event_t *event = NULL((void*)0); | |||
| 2302 | char *tmp = NULL((void*)0); | |||
| 2303 | skinny_check_data_length(request, sizeof(request->data.data))if (request->length < sizeof(request->data.data)+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2303, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.data)+ 4); return SWITCH_STATUS_FALSE; }; | |||
| 2304 | skinny_check_data_length(request, sizeof(request->data.data) + request->data.data.data_length - 1)if (request->length < sizeof(request->data.data) + request ->data.data.data_length - 1 +4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG , "skinny_server.c", (const char *)__func__, 2304, ((void*)0) , SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.data) + request->data.data.data_length - 1 +4); return SWITCH_STATUS_FALSE ; }; | |||
| 2305 | ||||
| 2306 | /* skinny::device_to_user event */ | |||
| 2307 | skinny_device_event(listener, &event, SWITCH_EVENT_CUSTOM, SKINNY_EVENT_DEVICE_TO_USER"skinny::device_to_user"); | |||
| 2308 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Message-Id", "%d", request->type); | |||
| 2309 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Message-Id-String", "%s", skinny_message_type2str(request->type)); | |||
| 2310 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Application-Id", "%d", request->data.data.application_id); | |||
| 2311 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Line-Instance", "%d", request->data.data.line_instance); | |||
| 2312 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Call-Id", "%d", request->data.data.call_id); | |||
| 2313 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Transaction-Id", "%d", request->data.data.transaction_id); | |||
| 2314 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Data-Length", "%d", request->data.data.data_length); | |||
| 2315 | ||||
| 2316 | tmp = malloc(request->data.data.data_length + 1); | |||
| 2317 | memcpy(tmp, request->data.data.data, request->data.data.data_length); | |||
| 2318 | ||||
| 2319 | /* Ensure that the body is null-terminated */ | |||
| 2320 | tmp[request->data.data.data_length] = '\0'; | |||
| 2321 | switch_event_add_body(event, "%s", tmp); | |||
| 2322 | ||||
| 2323 | switch_safe_free(tmp)if (tmp) {free(tmp);tmp=((void*)0);}; | |||
| 2324 | ||||
| 2325 | switch_event_fire(&event)switch_event_fire_detailed("skinny_server.c", (const char * ) (const char *)__func__, 2325, &event, ((void*)0)); | |||
| 2326 | ||||
| 2327 | return SWITCH_STATUS_SUCCESS; | |||
| 2328 | } | |||
| 2329 | ||||
| 2330 | switch_status_t skinny_handle_service_url_stat_request(listener_t *listener, skinny_message_t *request) | |||
| 2331 | { | |||
| 2332 | skinny_message_t *message; | |||
| 2333 | struct service_url_stat_res_message *button = NULL((void*)0); | |||
| 2334 | ||||
| 2335 | skinny_check_data_length(request, sizeof(request->data.service_url_req))if (request->length < sizeof(request->data.service_url_req )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 2335, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.service_url_req )+4); return SWITCH_STATUS_FALSE; }; | |||
| 2336 | ||||
| 2337 | skinny_create_message(message, SERVICE_URL_STAT_RES_MESSAGE, service_url_res)message = calloc(1, 12 + sizeof(message->data.service_url_res )); message->type = 0x012F; message->length = 4 + sizeof (message->data.service_url_res); | |||
| 2338 | ||||
| 2339 | skinny_service_url_get(listener, request->data.service_url_req.service_url_index, &button); | |||
| 2340 | ||||
| 2341 | memcpy(&message->data.service_url_res, button, sizeof(struct service_url_stat_res_message)); | |||
| 2342 | ||||
| 2343 | skinny_send_reply(listener, message, SWITCH_TRUE)skinny_perform_send_reply(listener, "skinny_server.c", (const char *)__func__, 2343, message, SWITCH_TRUE); | |||
| 2344 | ||||
| 2345 | return SWITCH_STATUS_SUCCESS; | |||
| 2346 | } | |||
| 2347 | ||||
| 2348 | switch_status_t skinny_handle_feature_stat_request(listener_t *listener, skinny_message_t *request) | |||
| 2349 | { | |||
| 2350 | skinny_message_t *message; | |||
| 2351 | struct feature_stat_res_message *button = NULL((void*)0); | |||
| 2352 | ||||
| 2353 | skinny_check_data_length(request, sizeof(request->data.feature_req))if (request->length < sizeof(request->data.feature_req )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 2353, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.feature_req )+4); return SWITCH_STATUS_FALSE; }; | |||
| 2354 | ||||
| 2355 | skinny_create_message(message, FEATURE_STAT_RES_MESSAGE, feature_res)message = calloc(1, 12 + sizeof(message->data.feature_res) ); message->type = 0x011F; message->length = 4 + sizeof (message->data.feature_res); | |||
| 2356 | ||||
| 2357 | skinny_feature_get(listener, request->data.feature_req.feature_index, &button); | |||
| 2358 | ||||
| 2359 | memcpy(&message->data.feature_res, button, sizeof(struct feature_stat_res_message)); | |||
| 2360 | ||||
| 2361 | skinny_send_reply(listener, message, SWITCH_TRUE)skinny_perform_send_reply(listener, "skinny_server.c", (const char *)__func__, 2361, message, SWITCH_TRUE); | |||
| 2362 | ||||
| 2363 | return SWITCH_STATUS_SUCCESS; | |||
| 2364 | } | |||
| 2365 | ||||
| 2366 | switch_status_t skinny_handle_extended_data_message(listener_t *listener, skinny_message_t *request) | |||
| 2367 | { | |||
| 2368 | switch_event_t *event = NULL((void*)0); | |||
| 2369 | char *tmp = NULL((void*)0); | |||
| 2370 | skinny_check_data_length(request, sizeof(request->data.extended_data))if (request->length < sizeof(request->data.extended_data )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 2370, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.extended_data )+4); return SWITCH_STATUS_FALSE; }; | |||
| 2371 | skinny_check_data_length(request, sizeof(request->data.extended_data)+request->data.extended_data.data_length-1)if (request->length < sizeof(request->data.extended_data )+request->data.extended_data.data_length-1 +4) { switch_log_printf (SWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 2371, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.extended_data )+request->data.extended_data.data_length-1 +4); return SWITCH_STATUS_FALSE ; }; | |||
| 2372 | ||||
| 2373 | /* skinny::device_to_user event */ | |||
| 2374 | skinny_device_event(listener, &event, SWITCH_EVENT_CUSTOM, SKINNY_EVENT_DEVICE_TO_USER"skinny::device_to_user"); | |||
| 2375 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Message-Id", "%d", request->type); | |||
| 2376 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Message-Id-String", "%s", skinny_message_type2str(request->type)); | |||
| 2377 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Application-Id", "%d", request->data.extended_data.application_id); | |||
| 2378 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Line-Instance", "%d", request->data.extended_data.line_instance); | |||
| 2379 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Call-Id", "%d", request->data.extended_data.call_id); | |||
| 2380 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Transaction-Id", "%d", request->data.extended_data.transaction_id); | |||
| 2381 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Data-Length", "%d", request->data.extended_data.data_length); | |||
| 2382 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Sequence-Flag", "%d", request->data.extended_data.sequence_flag); | |||
| 2383 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Display-Priority", "%d", request->data.extended_data.display_priority); | |||
| 2384 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Conference-Id", "%d", request->data.extended_data.conference_id); | |||
| 2385 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-App-Instance-Id", "%d", request->data.extended_data.app_instance_id); | |||
| 2386 | switch_event_add_header(event, SWITCH_STACK_BOTTOM, "Skinny-DeviceToUser-Routing-Id", "%d", request->data.extended_data.routing_id); | |||
| 2387 | ||||
| 2388 | tmp = malloc(request->data.data.data_length + 1); | |||
| 2389 | memcpy(tmp, request->data.data.data, request->data.data.data_length); | |||
| 2390 | ||||
| 2391 | /* Ensure that the body is null-terminated */ | |||
| 2392 | tmp[request->data.data.data_length] = '\0'; | |||
| 2393 | switch_event_add_body(event, "%s", tmp); | |||
| 2394 | ||||
| 2395 | switch_safe_free(tmp)if (tmp) {free(tmp);tmp=((void*)0);}; | |||
| 2396 | switch_event_fire(&event)switch_event_fire_detailed("skinny_server.c", (const char * ) (const char *)__func__, 2396, &event, ((void*)0)); | |||
| 2397 | ||||
| 2398 | return SWITCH_STATUS_SUCCESS; | |||
| 2399 | } | |||
| 2400 | ||||
| 2401 | switch_status_t skinny_handle_dialed_phone_book_message(listener_t *listener, skinny_message_t *request) | |||
| 2402 | { | |||
| 2403 | skinny_message_t *message; | |||
| 2404 | ||||
| 2405 | skinny_check_data_length(request, sizeof(request->data.dialed_phone_book))if (request->length < sizeof(request->data.dialed_phone_book )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 2405, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.dialed_phone_book )+4); return SWITCH_STATUS_FALSE; }; | |||
| 2406 | ||||
| 2407 | skinny_create_message(message, DIALED_PHONE_BOOK_ACK_MESSAGE, dialed_phone_book_ack)message = calloc(1, 12 + sizeof(message->data.dialed_phone_book_ack )); message->type = 0x0152; message->length = 4 + sizeof (message->data.dialed_phone_book_ack); | |||
| 2408 | ||||
| 2409 | message->data.dialed_phone_book_ack.number_index = request->data.dialed_phone_book.number_index; | |||
| 2410 | message->data.dialed_phone_book_ack.line_instance = request->data.dialed_phone_book.line_instance; | |||
| 2411 | message->data.dialed_phone_book_ack.unknown = request->data.dialed_phone_book.unknown; | |||
| 2412 | message->data.dialed_phone_book_ack.unknown2 = 0; | |||
| 2413 | ||||
| 2414 | #if 0 | |||
| 2415 | /* Not sure why this isn't being sent at this point, need to investigate */ | |||
| 2416 | skinny_log_l_ffl(listener, file, func, line, SWITCH_LOG_DEBUG,switch_log_printf( SWITCH_CHANNEL_ID_LOG, file, func, line, ( (void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Sending Handle Dialed Phone Book Ack Message with Number Index (%d), Line Instance (%d)\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, request->data.dialed_phone_book.number_index, request->data.dialed_phone_book.line_instance) | |||
| 2417 | "Sending Handle Dialed Phone Book Ack Message with Number Index (%d), Line Instance (%d)\n",switch_log_printf( SWITCH_CHANNEL_ID_LOG, file, func, line, ( (void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Sending Handle Dialed Phone Book Ack Message with Number Index (%d), Line Instance (%d)\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, request->data.dialed_phone_book.number_index, request->data.dialed_phone_book.line_instance) | |||
| 2418 | request->data.dialed_phone_book.number_index, request->data.dialed_phone_book.line_instance)switch_log_printf( SWITCH_CHANNEL_ID_LOG, file, func, line, ( (void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Sending Handle Dialed Phone Book Ack Message with Number Index (%d), Line Instance (%d)\n" , (_zstr(listener->device_name) ? "_undef_" : listener-> device_name), listener->device_instance, (_zstr(listener-> remote_ip) ? "_undef_" : listener->remote_ip), listener-> remote_port, request->data.dialed_phone_book.number_index, request->data.dialed_phone_book.line_instance); | |||
| 2419 | ||||
| 2420 | return skinny_send_reply_quiet(listener, message, SWITCH_TRUE)skinny_perform_send_reply_quiet(listener, "skinny_server.c", ( const char *)__func__, 2420, message, SWITCH_TRUE); | |||
| 2421 | #else | |||
| 2422 | switch_safe_free(message)if (message) {free(message);message=((void*)0);}; | |||
| 2423 | return SWITCH_STATUS_SUCCESS; | |||
| 2424 | #endif | |||
| 2425 | } | |||
| 2426 | ||||
| 2427 | switch_status_t skinny_handle_accessory_status_message(listener_t *listener, skinny_message_t *request) | |||
| 2428 | { | |||
| 2429 | char *sql; | |||
| 2430 | ||||
| 2431 | skinny_check_data_length(request, sizeof(request->data.accessory_status))if (request->length < sizeof(request->data.accessory_status )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 2431, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.accessory_status )+4); return SWITCH_STATUS_FALSE; }; | |||
| 2432 | ||||
| 2433 | switch(request->data.accessory_status.accessory_id) { | |||
| 2434 | case SKINNY_ACCESSORY_HEADSET: | |||
| 2435 | if ((sql = switch_mprintf( | |||
| 2436 | "UPDATE skinny_devices SET headset=%d WHERE name='%q' and instance=%d", | |||
| 2437 | request->data.accessory_status.accessory_status, | |||
| 2438 | listener->device_name, | |||
| 2439 | listener->device_instance | |||
| 2440 | ))) { | |||
| 2441 | skinny_execute_sql(listener->profile, sql, listener->profile->sql_mutex); | |||
| 2442 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 2443 | } | |||
| 2444 | break; | |||
| 2445 | case SKINNY_ACCESSORY_HANDSET: | |||
| 2446 | if ((sql = switch_mprintf( | |||
| 2447 | "UPDATE skinny_devices SET handset=%d WHERE name='%q' and instance=%d", | |||
| 2448 | request->data.accessory_status.accessory_status, | |||
| 2449 | listener->device_name, | |||
| 2450 | listener->device_instance | |||
| 2451 | ))) { | |||
| 2452 | skinny_execute_sql(listener->profile, sql, listener->profile->sql_mutex); | |||
| 2453 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 2454 | } | |||
| 2455 | break; | |||
| 2456 | case SKINNY_ACCESSORY_SPEAKER: | |||
| 2457 | if ((sql = switch_mprintf( | |||
| 2458 | "UPDATE skinny_devices SET speaker=%d WHERE name='%q' and instance=%d", | |||
| 2459 | request->data.accessory_status.accessory_status, | |||
| 2460 | listener->device_name, | |||
| 2461 | listener->device_instance | |||
| 2462 | ))) { | |||
| 2463 | skinny_execute_sql(listener->profile, sql, listener->profile->sql_mutex); | |||
| 2464 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 2465 | } | |||
| 2466 | break; | |||
| 2467 | } | |||
| 2468 | ||||
| 2469 | return SWITCH_STATUS_SUCCESS; | |||
| 2470 | } | |||
| 2471 | ||||
| 2472 | switch_status_t skinny_handle_updatecapabilities(listener_t *listener, skinny_message_t *request) | |||
| 2473 | { | |||
| 2474 | char *sql; | |||
| 2475 | skinny_profile_t *profile; | |||
| 2476 | ||||
| 2477 | uint32_t i = 0; | |||
| 2478 | uint32_t n = 0; | |||
| 2479 | char *codec_order[SKINNY_MAX_CAPABILITIES18]; | |||
| 2480 | char *codec_string; | |||
| 2481 | ||||
| 2482 | size_t string_len, string_pos, pos; | |||
| 2483 | ||||
| 2484 | switch_assert(listener->profile)((listener->profile) ? (void) (0) : __assert_fail ("listener->profile" , "skinny_server.c", 2484, __PRETTY_FUNCTION__)); | |||
| 2485 | switch_assert(listener->device_name)((listener->device_name) ? (void) (0) : __assert_fail ("listener->device_name" , "skinny_server.c", 2485, __PRETTY_FUNCTION__)); | |||
| 2486 | ||||
| 2487 | profile = listener->profile; | |||
| 2488 | ||||
| 2489 | skinny_check_data_length(request, sizeof(request->data.upd_cap.audio_cap_count))if (request->length < sizeof(request->data.upd_cap.audio_cap_count )+4) { switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c" , (const char *)__func__, 2489, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.upd_cap .audio_cap_count)+4); return SWITCH_STATUS_FALSE; }; | |||
| 2490 | ||||
| 2491 | n = request->data.upd_cap.audio_cap_count; | |||
| 2492 | if (n > SKINNY_MAX_CAPABILITIES18) { | |||
| 2493 | n = SKINNY_MAX_CAPABILITIES18; | |||
| 2494 | } | |||
| 2495 | string_len = -1; | |||
| 2496 | ||||
| 2497 | skinny_check_data_length(request, sizeof(request->data.upd_cap.audio_cap_count) + n * sizeof(request->data.upd_cap.audioCaps[0]))if (request->length < sizeof(request->data.upd_cap.audio_cap_count ) + n * sizeof(request->data.upd_cap.audioCaps[0])+4) { switch_log_printf (SWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 2497, ((void*)0), SWITCH_LOG_ERROR, "Received Too Short Skinny Message %s (type=%x,length=%d), expected %" "ld" ".\n", skinny_message_type2str(request->type), request ->type, request->length, sizeof(request->data.upd_cap .audio_cap_count) + n * sizeof(request->data.upd_cap.audioCaps [0])+4); return SWITCH_STATUS_FALSE; }; | |||
| 2498 | ||||
| 2499 | for (i = 0; i < n; i++) { | |||
| 2500 | char *codec = skinny_codec2string(request->data.upd_cap.audioCaps[i].payload_capability); | |||
| 2501 | codec_order[i] = codec; | |||
| 2502 | string_len += strlen(codec)+1; | |||
| 2503 | } | |||
| 2504 | i = 0; | |||
| 2505 | pos = 0; | |||
| 2506 | codec_string = switch_core_alloc(listener->pool, string_len+1)switch_core_perform_alloc(listener->pool, string_len+1, "skinny_server.c" , (const char *)__func__, 2506); | |||
| 2507 | for (string_pos = 0; string_pos < string_len; string_pos++) { | |||
| 2508 | char *codec = codec_order[i]; | |||
| ||||
| 2509 | switch_assert(i < n)((i < n) ? (void) (0) : __assert_fail ("i < n", "skinny_server.c" , 2509, __PRETTY_FUNCTION__)); | |||
| 2510 | if(pos == strlen(codec)) { | |||
| 2511 | codec_string[string_pos] = ','; | |||
| 2512 | i++; | |||
| 2513 | pos = 0; | |||
| 2514 | } else { | |||
| 2515 | codec_string[string_pos] = codec[pos++]; | |||
| 2516 | } | |||
| 2517 | } | |||
| 2518 | codec_string[string_len] = '\0'; | |||
| 2519 | if ((sql = switch_mprintf( | |||
| 2520 | "UPDATE skinny_devices SET codec_string='%q' WHERE name='%q'", | |||
| 2521 | codec_string, | |||
| 2522 | listener->device_name | |||
| 2523 | ))) { | |||
| 2524 | skinny_execute_sql(profile, sql, profile->sql_mutex); | |||
| 2525 | switch_safe_free(sql)if (sql) {free(sql);sql=((void*)0);}; | |||
| 2526 | } | |||
| 2527 | switch_log_printf(SWITCH_CHANNEL_LOGSWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 2527, ((void*)0), SWITCH_LOG_DEBUG, | |||
| 2528 | "Codecs %s supported.\n", codec_string); | |||
| 2529 | return SWITCH_STATUS_SUCCESS; | |||
| 2530 | } | |||
| 2531 | ||||
| 2532 | ||||
| 2533 | switch_status_t skinny_handle_server_req_message(listener_t *listener, skinny_message_t *request) | |||
| 2534 | { | |||
| 2535 | skinny_profile_t *profile; | |||
| 2536 | ||||
| 2537 | profile = listener->profile; | |||
| 2538 | ||||
| 2539 | skinny_log_l(listener, SWITCH_LOG_INFO, "Received Server Request Message (length=%d).\n", request->length)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2539, ((void*)0), SWITCH_LOG_INFO, "[%s:%d @ %s:%d] " "Received Server Request Message (length=%d).\n", (_zstr(listener ->device_name) ? "_undef_" : listener->device_name), listener ->device_instance, (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip), listener->remote_port, request ->length); | |||
| 2540 | ||||
| 2541 | send_srvreq_response(listener, profile->ip, profile->port)perform_send_srvreq_response(listener, "skinny_server.c", (const char *)__func__, 2541, profile->ip, profile->port); | |||
| 2542 | return SWITCH_STATUS_SUCCESS; | |||
| 2543 | } | |||
| 2544 | ||||
| 2545 | switch_status_t skinny_handle_xml_alarm(listener_t *listener, skinny_message_t *request) | |||
| 2546 | { | |||
| 2547 | switch_event_t *event = NULL((void*)0); | |||
| 2548 | char *tmp = NULL((void*)0); | |||
| 2549 | ||||
| 2550 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Received XML alarm (length=%d).\n", request->length)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2550, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Received XML alarm (length=%d).\n", (_zstr(listener->device_name ) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port, request->length); | |||
| 2551 | /* skinny::xml_alarm event */ | |||
| 2552 | skinny_device_event(listener, &event, SWITCH_EVENT_CUSTOM, SKINNY_EVENT_XML_ALARM"skinny::xml_alarm"); | |||
| 2553 | /* Ensure that the body is null-terminated */ | |||
| 2554 | tmp = malloc(request->length - 4 + 1); | |||
| 2555 | memcpy(tmp, request->data.as_char, request->length - 4); | |||
| 2556 | tmp[request->length - 4] = '\0'; | |||
| 2557 | switch_event_add_body(event, "%s", tmp); | |||
| 2558 | switch_safe_free(tmp)if (tmp) {free(tmp);tmp=((void*)0);}; | |||
| 2559 | switch_event_fire(&event)switch_event_fire_detailed("skinny_server.c", (const char * ) (const char *)__func__, 2559, &event, ((void*)0)); | |||
| 2560 | ||||
| 2561 | return SWITCH_STATUS_SUCCESS; | |||
| 2562 | } | |||
| 2563 | ||||
| 2564 | switch_status_t skinny_handle_request(listener_t *listener, skinny_message_t *request) | |||
| 2565 | { | |||
| 2566 | if (listener->profile->debug >= 10 || | |||
| 2567 | (listener->profile->debug >= 9 && request->type != KEEP_ALIVE_MESSAGE0x0000)) { | |||
| 2568 | skinny_log_l(listener, SWITCH_LOG_DEBUG, "Received %s (type=%x,length=%d).\n",switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2569, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Received %s (type=%x,length=%d).\n", (_zstr(listener->device_name ) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port, skinny_message_type2str(request-> type), request->type, request->length) | |||
| 2569 | skinny_message_type2str(request->type), request->type, request->length)switch_log_printf(SWITCH_CHANNEL_ID_LOG, "skinny_server.c", ( const char *)__func__, 2569, ((void*)0), SWITCH_LOG_DEBUG, "[%s:%d @ %s:%d] " "Received %s (type=%x,length=%d).\n", (_zstr(listener->device_name ) ? "_undef_" : listener->device_name), listener->device_instance , (_zstr(listener->remote_ip) ? "_undef_" : listener->remote_ip ), listener->remote_port, skinny_message_type2str(request-> type), request->type, request->length); | |||
| 2570 | } | |||
| 2571 | if(zstr(listener->device_name)_zstr(listener->device_name) && request->type != REGISTER_MESSAGE0x0001 && request->type != ALARM_MESSAGE0x0020 && request->type != XML_ALARM_MESSAGE0x015A && request->type != KEEP_ALIVE_MESSAGE0x0000) { | |||
| 2572 | switch_log_printf(SWITCH_CHANNEL_LOGSWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 2572, ((void*)0), SWITCH_LOG_WARNING, | |||
| 2573 | "Device should send a register message first. Received %s (type=%x,length=%d).\n", skinny_message_type2str(request->type), request->type, request->length); | |||
| 2574 | return SWITCH_STATUS_FALSE; | |||
| 2575 | } | |||
| 2576 | switch(request->type) { | |||
| ||||
| 2577 | case KEEP_ALIVE_MESSAGE0x0000: | |||
| 2578 | return skinny_handle_keep_alive_message(listener, request); | |||
| 2579 | case REGISTER_MESSAGE0x0001: | |||
| 2580 | return skinny_handle_register(listener, request); | |||
| 2581 | case PORT_MESSAGE0x0002: | |||
| 2582 | return skinny_handle_port_message(listener, request); | |||
| 2583 | case KEYPAD_BUTTON_MESSAGE0x0003: | |||
| 2584 | return skinny_handle_keypad_button_message(listener, request); | |||
| 2585 | case ENBLOC_CALL_MESSAGE0x0004: | |||
| 2586 | return skinny_handle_enbloc_call_message(listener, request); | |||
| 2587 | case STIMULUS_MESSAGE0x0005: | |||
| 2588 | return skinny_handle_stimulus_message(listener, request); | |||
| 2589 | case OFF_HOOK_MESSAGE0x0006: | |||
| 2590 | return skinny_handle_off_hook_message(listener, request); | |||
| 2591 | case ON_HOOK_MESSAGE0x0007: | |||
| 2592 | return skinny_handle_on_hook_message(listener, request); | |||
| 2593 | case FORWARD_STAT_REQ_MESSAGE0x0009: | |||
| 2594 | return skinny_handle_forward_stat_req_message(listener, request); | |||
| 2595 | case SPEED_DIAL_STAT_REQ_MESSAGE0x000A: | |||
| 2596 | return skinny_handle_speed_dial_stat_request(listener, request); | |||
| 2597 | case LINE_STAT_REQ_MESSAGE0x000B: | |||
| 2598 | return skinny_handle_line_stat_request(listener, request); | |||
| 2599 | case CONFIG_STAT_REQ_MESSAGE0x000C: | |||
| 2600 | return skinny_handle_config_stat_request(listener, request); | |||
| 2601 | case TIME_DATE_REQ_MESSAGE0x000D: | |||
| 2602 | return skinny_handle_time_date_request(listener, request); | |||
| 2603 | case BUTTON_TEMPLATE_REQ_MESSAGE0x000E: | |||
| 2604 | return skinny_handle_button_template_request(listener, request); | |||
| 2605 | case VERSION_REQ_MESSAGE0x000F: | |||
| 2606 | return skinny_handle_version_request(listener, request); | |||
| 2607 | case CAPABILITIES_RES_MESSAGE0x0010: | |||
| 2608 | return skinny_handle_capabilities_response(listener, request); | |||
| 2609 | case ALARM_MESSAGE0x0020: | |||
| 2610 | return skinny_handle_alarm(listener, request); | |||
| 2611 | case OPEN_RECEIVE_CHANNEL_ACK_MESSAGE0x0022: | |||
| 2612 | return skinny_handle_open_receive_channel_ack_message(listener, request); | |||
| 2613 | case SOFT_KEY_SET_REQ_MESSAGE0x0025: | |||
| 2614 | return skinny_handle_soft_key_set_request(listener, request); | |||
| 2615 | case SOFT_KEY_EVENT_MESSAGE0x0026: | |||
| 2616 | return skinny_handle_soft_key_event_message(listener, request); | |||
| 2617 | case UNREGISTER_MESSAGE0x0027: | |||
| 2618 | return skinny_handle_unregister(listener, request); | |||
| 2619 | case SOFT_KEY_TEMPLATE_REQ_MESSAGE0x0028: | |||
| 2620 | return skinny_handle_soft_key_template_request(listener, request); | |||
| 2621 | case MEDIA_RESOURCE_MESSAGE0x002C: | |||
| 2622 | return skinny_handle_media_resource_message(listener, request); | |||
| 2623 | case HEADSET_STATUS_MESSAGE0x002B: | |||
| 2624 | return skinny_headset_status_message(listener, request); | |||
| 2625 | case REGISTER_AVAILABLE_LINES_MESSAGE0x002D: | |||
| 2626 | return skinny_handle_register_available_lines_message(listener, request); | |||
| 2627 | case DEVICE_TO_USER_DATA_MESSAGE0x002E: | |||
| 2628 | return skinny_handle_data_message(listener, request); | |||
| 2629 | case DEVICE_TO_USER_DATA_RESPONSE_MESSAGE0x002F: | |||
| 2630 | return skinny_handle_data_message(listener, request); | |||
| 2631 | case SERVICE_URL_STAT_REQ_MESSAGE0x0033: | |||
| 2632 | return skinny_handle_service_url_stat_request(listener, request); | |||
| 2633 | case FEATURE_STAT_REQ_MESSAGE0x0034: | |||
| 2634 | return skinny_handle_feature_stat_request(listener, request); | |||
| 2635 | case DEVICE_TO_USER_DATA_VERSION1_MESSAGE0x0041: | |||
| 2636 | return skinny_handle_extended_data_message(listener, request); | |||
| 2637 | case DEVICE_TO_USER_DATA_RESPONSE_VERSION1_MESSAGE0x0042: | |||
| 2638 | return skinny_handle_extended_data_message(listener, request); | |||
| 2639 | case DIALED_PHONE_BOOK_MESSAGE0x0048: | |||
| 2640 | return skinny_handle_dialed_phone_book_message(listener, request); | |||
| 2641 | case ACCESSORY_STATUS_MESSAGE0x0049: | |||
| 2642 | return skinny_handle_accessory_status_message(listener, request); | |||
| 2643 | case XML_ALARM_MESSAGE0x015A: | |||
| 2644 | return skinny_handle_xml_alarm(listener, request); | |||
| 2645 | case UPDATE_CAPABILITIES_MESSAGE0x0030: | |||
| 2646 | return skinny_handle_updatecapabilities(listener, request); | |||
| 2647 | case SERVER_REQ_MESSAGE0x0012: | |||
| 2648 | return skinny_handle_server_req_message(listener, request); | |||
| 2649 | default: | |||
| 2650 | switch_log_printf(SWITCH_CHANNEL_LOGSWITCH_CHANNEL_ID_LOG, "skinny_server.c", (const char *)__func__ , 2650, ((void*)0), SWITCH_LOG_WARNING, | |||
| 2651 | "Unhandled %s (type=%x,length=%d).\n", skinny_message_type2str(request->type), request->type, request->length); | |||
| 2652 | return SWITCH_STATUS_SUCCESS; | |||
| 2653 | } | |||
| 2654 | } | |||
| 2655 | ||||
| 2656 | /* For Emacs: | |||
| 2657 | * Local Variables: | |||
| 2658 | * mode:c | |||
| 2659 | * indent-tabs-mode:t | |||
| 2660 | * tab-width:4 | |||
| 2661 | * c-basic-offset:4 | |||
| 2662 | * End: | |||
| 2663 | * For VIM: | |||
| 2664 | * vim:set softtabstop=4 shiftwidth=4 tabstop=4 noet: | |||
| 2665 | */ | |||
| 2666 |