FreeSWITCH API Documentation  1.7.0
Data Structures | Macros | Functions
switch_ivr.c File Reference
#include <switch.h>
#include <switch_ivr.h>
+ Include dependency graph for switch_ivr.c:

Go to the source code of this file.

Data Structures

struct  media_job_t
 
struct  switch_ivr_digit_stream_parser
 
struct  switch_ivr_digit_stream
 

Macros

#define add_stat(_x, _i, _s)
 
#define add_stat_double(_x, _i, _s)
 
#define add_jstat(_j, _i, _s)
 
#define START_SAMPLES   32768
 

Functions

switch_status_t switch_ivr_sound_test (switch_core_session_t *session)
 
switch_status_t switch_ivr_sleep (switch_core_session_t *session, uint32_t ms, switch_bool_t sync, switch_input_args_t *args)
 Wait for time to pass for a specified number of milliseconds. More...
 
static void *SWITCH_THREAD_FUNC unicast_thread_run (switch_thread_t *thread, void *obj)
 
static void unicast_thread_launch (switch_unicast_conninfo_t *conninfo)
 
switch_status_t switch_ivr_deactivate_unicast (switch_core_session_t *session)
 
switch_status_t switch_ivr_activate_unicast (switch_core_session_t *session, char *local_ip, switch_port_t local_port, char *remote_ip, switch_port_t remote_port, char *transport, char *flags)
 
switch_status_t switch_ivr_parse_event (switch_core_session_t *session, switch_event_t *event)
 
switch_status_t switch_ivr_parse_next_event (switch_core_session_t *session)
 
switch_status_t switch_ivr_process_indications (switch_core_session_t *session, switch_core_session_message_t *message)
 
switch_status_t switch_ivr_parse_all_messages (switch_core_session_t *session)
 
switch_status_t switch_ivr_parse_signal_data (switch_core_session_t *session, switch_bool_t all, switch_bool_t only_session_thread)
 
switch_status_t switch_ivr_parse_all_signal_data (switch_core_session_t *session)
 
switch_status_t switch_ivr_parse_next_signal_data (switch_core_session_t *session)
 
switch_status_t switch_ivr_parse_all_events (switch_core_session_t *session)
 Parse all commands from an event. More...
 
switch_status_t switch_ivr_park (switch_core_session_t *session, switch_input_args_t *args)
 
switch_status_t switch_ivr_collect_digits_callback (switch_core_session_t *session, switch_input_args_t *args, uint32_t digit_timeout, uint32_t abs_timeout)
 Wait for DTMF digits calling a pluggable callback function when digits are collected. More...
 
switch_status_t switch_ivr_collect_digits_count (switch_core_session_t *session, char *buf, switch_size_t buflen, switch_size_t maxdigits, const char *terminators, char *terminator, uint32_t first_timeout, uint32_t digit_timeout, uint32_t abs_timeout)
 Wait for specified number of DTMF digits, untile terminator is received or until the channel hangs up. More...
 
switch_status_t switch_ivr_hold (switch_core_session_t *session, const char *message, switch_bool_t moh)
 Signal the session with a protocol specific hold message. More...
 
switch_status_t switch_ivr_hold_uuid (const char *uuid, const char *message, switch_bool_t moh)
 Signal the session with a protocol specific hold message. More...
 
switch_status_t switch_ivr_hold_toggle_uuid (const char *uuid, const char *message, switch_bool_t moh)
 Toggles channel hold state of session. More...
 
switch_status_t switch_ivr_unhold (switch_core_session_t *session)
 Signal the session with a protocol specific unhold message. More...
 
switch_status_t switch_ivr_unhold_uuid (const char *uuid)
 Signal the session with a protocol specific unhold message. More...
 
switch_status_t switch_ivr_3p_media (const char *uuid, switch_media_flag_t flags)
 
switch_status_t switch_ivr_media (const char *uuid, switch_media_flag_t flags)
 Signal a session to request direct media access to it's remote end. More...
 
switch_status_t switch_ivr_3p_nomedia (const char *uuid, switch_media_flag_t flags)
 
switch_status_t switch_ivr_nomedia (const char *uuid, switch_media_flag_t flags)
 Signal a session to request indirect media allowing it to exchange media directly with another device. More...
 
static void *SWITCH_THREAD_FUNC media_thread_run (switch_thread_t *thread, void *obj)
 
void switch_ivr_bg_media (const char *uuid, switch_media_flag_t flags, switch_bool_t on, switch_bool_t is3p, uint32_t delay)
 
switch_status_t switch_ivr_session_transfer (switch_core_session_t *session, const char *extension, const char *dialplan, const char *context)
 
switch_status_t switch_ivr_transfer_variable (switch_core_session_t *sessa, switch_core_session_t *sessb, char *var)
 Transfer variables from one session to another. More...
 
switch_status_t switch_ivr_digit_stream_parser_new (switch_memory_pool_t *pool, switch_ivr_digit_stream_parser_t **parser)
 Create a digit stream parser object. More...
 
switch_status_t switch_ivr_digit_stream_parser_destroy (switch_ivr_digit_stream_parser_t *parser)
 Destroy a digit stream parser object. More...
 
switch_status_t switch_ivr_digit_stream_new (switch_ivr_digit_stream_parser_t *parser, switch_ivr_digit_stream_t **stream)
 Create a new digit stream object. More...
 
switch_status_t switch_ivr_digit_stream_destroy (switch_ivr_digit_stream_t **stream)
 Destroys a digit stream object. More...
 
switch_status_t switch_ivr_digit_stream_parser_set_event (switch_ivr_digit_stream_parser_t *parser, char *digits, void *data)
 Set a digit string to action mapping. More...
 
switch_status_t switch_ivr_digit_stream_parser_del_event (switch_ivr_digit_stream_parser_t *parser, char *digits)
 Delete a string to action mapping. More...
 
void * switch_ivr_digit_stream_parser_feed (switch_ivr_digit_stream_parser_t *parser, switch_ivr_digit_stream_t *stream, char digit)
 Feed digits collected into the stream for event match testing. More...
 
switch_status_t switch_ivr_digit_stream_reset (switch_ivr_digit_stream_t *stream)
 Reset the collected digit stream to nothing. More...
 
switch_status_t switch_ivr_digit_stream_parser_set_terminator (switch_ivr_digit_stream_parser_t *parser, char digit)
 Set a digit string terminator. More...
 
int switch_ivr_set_xml_profile_data (switch_xml_t xml, switch_caller_profile_t *caller_profile, int off)
 
int switch_ivr_set_xml_call_stats (switch_xml_t xml, switch_core_session_t *session, int off, switch_media_type_t type)
 
static int switch_ivr_set_xml_chan_var (switch_xml_t xml, const char *var, const char *val, int off)
 
int switch_ivr_set_xml_chan_vars (switch_xml_t xml, switch_channel_t *channel, int off)
 
switch_status_t switch_ivr_generate_xml_cdr (switch_core_session_t *session, switch_xml_t *xml_cdr)
 Generate an XML CDR report. More...
 
static void switch_ivr_set_json_profile_data (cJSON *json, switch_caller_profile_t *caller_profile)
 
void switch_ivr_set_json_call_stats (cJSON *json, switch_core_session_t *session, switch_media_type_t type)
 
static void switch_ivr_set_json_chan_vars (cJSON *json, switch_channel_t *channel, switch_bool_t urlencode)
 
switch_status_t switch_ivr_generate_json_cdr (switch_core_session_t *session, cJSON **json_cdr, switch_bool_t urlencode)
 Generate an JSON CDR report. More...
 
void switch_ivr_park_session (switch_core_session_t *session)
 
void switch_ivr_delay_echo (switch_core_session_t *session, uint32_t delay_ms)
 
switch_status_t switch_ivr_say (switch_core_session_t *session, const char *tosay, const char *module_name, const char *say_type, const char *say_method, const char *say_gender, switch_input_args_t *args)
 
switch_status_t switch_ivr_say_string (switch_core_session_t *session, const char *lang, const char *ext, const char *tosay, const char *module_name, const char *say_type, const char *say_method, const char *say_gender, char **rstr)
 
static const char * get_prefixed_str (char *buffer, size_t buffer_size, const char *prefix, size_t prefix_size, const char *str)
 
switch_status_t switch_ivr_set_user_xml (switch_core_session_t *session, const char *prefix, const char *user, const char *domain, switch_xml_t x_user)
 
switch_status_t switch_ivr_set_user (switch_core_session_t *session, const char *data)
 
switch_bool_t switch_ivr_uuid_exists (const char *uuid)
 
switch_bool_t switch_ivr_uuid_force_exists (const char *uuid)
 
switch_status_t switch_ivr_process_fh (switch_core_session_t *session, const char *cmd, switch_file_handle_t *fhp)
 
switch_status_t switch_ivr_insert_file (switch_core_session_t *session, const char *file, const char *insert_file, switch_size_t sample_point)
 
switch_status_t switch_ivr_create_message_reply (switch_event_t **reply, switch_event_t *message, const char *new_proto)
 
char * switch_ivr_check_presence_mapping (const char *exten_name, const char *domain_name)
 
switch_status_t switch_ivr_kill_uuid (const char *uuid, switch_call_cause_t cause)
 
switch_status_t switch_ivr_blind_transfer_ack (switch_core_session_t *session, switch_bool_t success)
 

Macro Definition Documentation

#define add_jstat (   _j,
  _i,
  _s 
)
Value:
switch_snprintf(var_val, sizeof(var_val), "%" SWITCH_SIZE_T_FMT, _i); \
cJSON * cJSON_CreateNumber(double num)
Definition: switch_json.c:541
int switch_snprintf(_Out_z_cap_(len) char *buf, _In_ switch_size_t len, _In_z_ _Printf_format_string_ const char *format,...)
void cJSON_AddItemToObject(cJSON *object, const char *string, cJSON *item)
Definition: switch_json.c:520
#define SWITCH_SIZE_T_FMT

Definition at line 3072 of file switch_ivr.c.

Referenced by switch_ivr_set_json_call_stats().

#define add_stat (   _x,
  _i,
  _s 
)
Value:
switch_snprintf(var_val, sizeof(var_val), "%" SWITCH_SIZE_T_FMT, _i); \
x_tmp = switch_xml_add_child_d(_x, _s, loff++); \
switch_xml_set_txt_d(x_tmp, var_val)
#define switch_xml_add_child_d(xml, name, off)
wrapper for switch_xml_add_child() that strdup()s name
Definition: switch_xml.h:269
int switch_snprintf(_Out_z_cap_(len) char *buf, _In_ switch_size_t len, _In_z_ _Printf_format_string_ const char *format,...)
#define switch_xml_set_txt_d(xml, txt)
wrapper for switch_xml_set_txt() that strdup()s txt \ sets the character content for the given tag an...
Definition: switch_xml.h:283
#define SWITCH_SIZE_T_FMT

Definition at line 2569 of file switch_ivr.c.

Referenced by switch_ivr_set_xml_call_stats().

#define add_stat_double (   _x,
  _i,
  _s 
)
Value:
switch_snprintf(var_val, sizeof(var_val), "%0.2f", _i); \
x_tmp = switch_xml_add_child_d(_x, _s, loff++); \
switch_xml_set_txt_d(x_tmp, var_val)
#define switch_xml_add_child_d(xml, name, off)
wrapper for switch_xml_add_child() that strdup()s name
Definition: switch_xml.h:269
int switch_snprintf(_Out_z_cap_(len) char *buf, _In_ switch_size_t len, _In_z_ _Printf_format_string_ const char *format,...)
#define switch_xml_set_txt_d(xml, txt)
wrapper for switch_xml_set_txt() that strdup()s txt \ sets the character content for the given tag an...
Definition: switch_xml.h:283

Definition at line 2574 of file switch_ivr.c.

Referenced by switch_ivr_set_xml_call_stats().

#define START_SAMPLES   32768

Definition at line 4007 of file switch_ivr.c.

Referenced by switch_ivr_insert_file().

Function Documentation

static const char* get_prefixed_str ( char *  buffer,
size_t  buffer_size,
const char *  prefix,
size_t  prefix_size,
const char *  str 
)
static

Definition at line 3736 of file switch_ivr.c.

Referenced by switch_ivr_set_user_xml().

3737 {
3738  size_t str_len;
3739 
3740  if (!buffer) {
3741  /*
3742  if buffer is null then it just returns the str without the prefix appended, otherwise buffer contains the prefix followed by the original string
3743  */
3744 
3745  return str;
3746  }
3747 
3748  str_len = strlen(str);
3749  memcpy(buffer, prefix, prefix_size);
3750 
3751  if (str_len + prefix_size + 1 > buffer_size) {
3752  memcpy(buffer + prefix_size, str, buffer_size - prefix_size - 1);
3753  buffer[buffer_size - prefix_size - 1] = '\0';
3754  } else {
3755  memcpy(buffer + prefix_size, str, str_len + 1);
3756  }
3757 
3758  return buffer;
3759 }
static void* SWITCH_THREAD_FUNC media_thread_run ( switch_thread_t thread,
void *  obj 
)
static

Definition at line 1988 of file switch_ivr.c.

References media_job_t::delay, media_job_t::flags, media_job_t::is3p, media_job_t::on, switch_ivr_3p_media(), switch_ivr_3p_nomedia(), switch_ivr_media(), switch_ivr_nomedia(), switch_yield, and media_job_t::uuid.

Referenced by switch_ivr_bg_media().

1989 {
1990  media_job_t *job = (media_job_t *) obj;
1991 
1992  if (job->delay) {
1993  switch_yield(job->delay * 1000);
1994  }
1995 
1996  if (job->on) {
1997  if (job->is3p) {
1998  switch_ivr_3p_media(job->uuid, job->flags);
1999  } else {
2000  switch_ivr_media(job->uuid, job->flags);
2001  }
2002  } else {
2003  if (job->is3p) {
2004  switch_ivr_3p_nomedia(job->uuid, job->flags);
2005  } else {
2006  switch_ivr_nomedia(job->uuid, job->flags);
2007  }
2008  }
2009 
2010  return NULL;
2011 }
const char * uuid
Definition: switch_ivr.c:1981
switch_status_t switch_ivr_nomedia(const char *uuid, switch_media_flag_t flags)
Signal a session to request indirect media allowing it to exchange media directly with another device...
Definition: switch_ivr.c:1880
switch_status_t switch_ivr_media(const char *uuid, switch_media_flag_t flags)
Signal a session to request direct media access to it's remote end.
Definition: switch_ivr.c:1674
#define switch_yield(ms)
Wait a desired number of microseconds and yield the CPU.
Definition: switch_utils.h:908
switch_bool_t on
Definition: switch_ivr.c:1983
uint32_t delay
Definition: switch_ivr.c:1985
switch_status_t switch_ivr_3p_nomedia(const char *uuid, switch_media_flag_t flags)
Definition: switch_ivr.c:1774
switch_media_flag_t flags
Definition: switch_ivr.c:1982
switch_bool_t is3p
Definition: switch_ivr.c:1984
switch_status_t switch_ivr_3p_media(const char *uuid, switch_media_flag_t flags)
Definition: switch_ivr.c:1564
switch_status_t switch_ivr_parse_event ( switch_core_session_t session,
switch_event_t event 
)

Definition at line 497 of file switch_ivr.c.

References CF_BREAK, CF_BRIDGED, CF_BROADCAST, CF_EVENT_LOCK, CF_EVENT_LOCK_PRI, CF_EVENT_PARSE, CF_STOP_BROADCAST, switch_event_header::name, switch_event_header::next, SFF_CNG, SMF_ECHO_ALEG, SMF_LOOP, SMF_REBRIDGE, switch_caller_extension_add_application(), switch_caller_extension_new(), SWITCH_CAUSE_NORMAL_CLEARING, switch_channel_audio_sync, switch_channel_clear_flag(), switch_channel_clear_flag_recursive(), switch_channel_get_hold_music(), switch_channel_get_hold_music_partner(), switch_channel_get_name(), switch_channel_get_partner_uuid(), switch_channel_hangup, switch_channel_media_ready, switch_channel_ready, SWITCH_CHANNEL_SESSION_LOG, switch_channel_set_flag, switch_channel_set_flag_recursive(), switch_channel_set_variable, switch_channel_set_variable_printf(), switch_channel_stop_broadcast, switch_channel_str2cause(), switch_channel_test_flag(), switch_channel_transfer_to_extension(), switch_channel_wait_for_flag(), switch_core_session_execute_application, switch_core_session_flush_private_events(), switch_core_session_get_channel(), switch_core_session_kill_channel, switch_core_session_locate, switch_core_session_read_frame(), switch_core_session_rwunlock(), switch_core_session_strdup, switch_event_get_body(), switch_event_get_header, SWITCH_FALSE, switch_hashfunc_default(), SWITCH_IO_FLAG_NONE, switch_is_moh(), switch_ivr_activate_unicast(), switch_ivr_broadcast(), switch_ivr_nomedia(), SWITCH_LOG_DEBUG, SWITCH_LOG_ERROR, switch_log_printf(), switch_micro_time_now(), SWITCH_READ_ACCEPTABLE, SWITCH_SIG_BREAK, SWITCH_STATUS_BREAK, SWITCH_STATUS_FALSE, SWITCH_STATUS_SUCCESS, switch_str_nil, switch_test_flag, SWITCH_TRUE, switch_true(), switch_event_header::value, and zstr.

Referenced by switch_ivr_park(), and switch_ivr_parse_next_event().

498 {
500  char *cmd = switch_event_get_header(event, "call-command");
501  unsigned long cmd_hash;
502  switch_ssize_t hlen = -1;
503  unsigned long CMD_EXECUTE = switch_hashfunc_default("execute", &hlen);
504  unsigned long CMD_HANGUP = switch_hashfunc_default("hangup", &hlen);
505  unsigned long CMD_NOMEDIA = switch_hashfunc_default("nomedia", &hlen);
506  unsigned long CMD_UNICAST = switch_hashfunc_default("unicast", &hlen);
507  unsigned long CMD_XFEREXT = switch_hashfunc_default("xferext", &hlen);
508  char *lead_frames = switch_event_get_header(event, "lead-frames");
509  char *event_lock = switch_event_get_header(event, "event-lock");
510  char *event_lock_pri = switch_event_get_header(event, "event-lock-pri");
512  int el = 0, elp = 0;
513 
514  if (zstr(cmd)) {
515  switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session), SWITCH_LOG_ERROR, "Invalid Command!\n");
516  return SWITCH_STATUS_FALSE;
517  }
518 
519  cmd_hash = switch_hashfunc_default(cmd, &hlen);
520 
522 
523  if (switch_true(event_lock)) {
525  el = 1;
526  }
527 
528  if (switch_true(event_lock_pri)) {
530  elp = 1;
531  }
532 
533  if (lead_frames && switch_channel_media_ready(channel)) {
534  switch_frame_t *read_frame;
535  int frame_count = atoi(lead_frames);
536  int max_frames = frame_count * 2;
537 
538  while (frame_count > 0 && --max_frames > 0) {
539  status = switch_core_session_read_frame(session, &read_frame, SWITCH_IO_FLAG_NONE, 0);
540  if (!SWITCH_READ_ACCEPTABLE(status)) {
541  goto done;
542  }
543  if (!switch_test_flag(read_frame, SFF_CNG)) {
544  frame_count--;
545  }
546  }
547  }
548 
549  if (cmd_hash == CMD_EXECUTE) {
550  char *app_name = switch_event_get_header(event, "execute-app-name");
551  char *event_uuid = switch_event_get_header(event, "event-uuid");
552  char *app_arg = switch_event_get_header(event, "execute-app-arg");
553  char *content_type = switch_event_get_header(event, "content-type");
554  char *loop_h = switch_event_get_header(event, "loops");
555  char *hold_bleg = switch_event_get_header(event, "hold-bleg");
556  int loops = 1;
557  int inner = 0;
558 
559  if (zstr(app_arg) && !zstr(content_type) && !strcasecmp(content_type, "text/plain")) {
560  app_arg = switch_event_get_body(event);
561  }
562 
563  if (loop_h) {
564  loops = atoi(loop_h);
565  }
566 
567  if (app_name) {
568  int x;
569  const char *b_uuid = NULL;
570  switch_core_session_t *b_session = NULL;
571 
573 
575  inner++;
576  hold_bleg = NULL;
577  }
578 
579  if (!switch_channel_test_flag(channel, CF_BROADCAST)) {
581  if (inner) {
582  inner--;
583  }
584  }
585 
586  if (hold_bleg && switch_true(hold_bleg)) {
587  if ((b_uuid = switch_channel_get_partner_uuid(channel))) {
588  const char *stream;
589  b_uuid = switch_core_session_strdup(session, b_uuid);
590 
591  if (!(stream = switch_channel_get_hold_music_partner(channel))) {
592  stream = switch_channel_get_hold_music(channel);
593  }
594 
595  if (stream && switch_is_moh(stream)) {
596  if ((b_session = switch_core_session_locate(b_uuid))) {
597  switch_channel_t *b_channel = switch_core_session_get_channel(b_session);
598  switch_status_t st;
599 
600  switch_ivr_broadcast(b_uuid, stream, SMF_ECHO_ALEG | SMF_LOOP);
601  st = switch_channel_wait_for_flag(b_channel, CF_BROADCAST, SWITCH_TRUE, 5000, NULL);
602  if (st != SWITCH_STATUS_SUCCESS &&
603  switch_channel_ready(channel) && switch_channel_ready(b_channel) && !switch_channel_test_flag(b_channel, CF_BROADCAST)) {
605  st = switch_channel_wait_for_flag(b_channel, CF_BROADCAST, SWITCH_TRUE, 5000, NULL);
606 
607  if (st != SWITCH_STATUS_SUCCESS &&
608  switch_channel_ready(channel) && switch_channel_ready(b_channel) && !switch_channel_test_flag(b_channel, CF_BROADCAST)) {
610  }
611  }
612  switch_core_session_rwunlock(b_session);
613  }
614  } else {
615  b_uuid = NULL;
616  }
617  }
618  }
619 
620  for (x = 0; x < loops || loops < 0; x++) {
621  switch_time_t b4, aftr;
622 
623  switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session), SWITCH_LOG_DEBUG, "%s Command Execute %s(%s)\n",
624  switch_channel_get_name(channel), app_name, switch_str_nil(app_arg));
625  b4 = switch_micro_time_now();
626 
627  if (event_uuid) {
628  switch_channel_set_variable(channel, "app_uuid", event_uuid);
629  }
630 
631  switch_channel_set_variable_printf(channel, "current_loop", "%d", x + 1);
632  switch_channel_set_variable_printf(channel, "total_loops", "%d", loops);
633 
634  if (switch_core_session_execute_application(session, app_name, app_arg) != SWITCH_STATUS_SUCCESS) {
636  break;
637  }
638 
639  aftr = switch_micro_time_now();
640  if (!switch_channel_ready(channel) || switch_channel_test_flag(channel, CF_STOP_BROADCAST) || aftr - b4 < 500000) {
641  break;
642  }
643  }
644 
645  switch_channel_set_variable(channel, "current_loop", NULL);
646  switch_channel_set_variable(channel, "total_loops", NULL);
647 
648  if (b_uuid) {
649  if ((b_session = switch_core_session_locate(b_uuid))) {
650  switch_channel_t *b_channel = switch_core_session_get_channel(b_session);
652  switch_channel_wait_for_flag(b_channel, CF_BROADCAST, SWITCH_FALSE, 5000, NULL);
653  switch_core_session_rwunlock(b_session);
654  }
655  }
656 
657  if (!inner) {
659  }
660 
664  }
665 
666  switch_channel_audio_sync(channel);
667  }
668  } else if (cmd_hash == CMD_UNICAST) {
669  char *local_ip = switch_event_get_header(event, "local-ip");
670  char *local_port = switch_event_get_header(event, "local-port");
671  char *remote_ip = switch_event_get_header(event, "remote-ip");
672  char *remote_port = switch_event_get_header(event, "remote-port");
673  char *transport = switch_event_get_header(event, "transport");
674  char *flags = switch_event_get_header(event, "flags");
675 
676  if (zstr(local_ip)) {
677  local_ip = "127.0.0.1";
678  }
679  if (zstr(remote_ip)) {
680  remote_ip = "127.0.0.1";
681  }
682  if (zstr(local_port)) {
683  local_port = "8025";
684  }
685  if (zstr(remote_port)) {
686  remote_port = "8026";
687  }
688  if (zstr(transport)) {
689  transport = "udp";
690  }
691 
692  switch_ivr_activate_unicast(session, local_ip, (switch_port_t) atoi(local_port), remote_ip, (switch_port_t) atoi(remote_port), transport, flags);
693 
694  } else if (cmd_hash == CMD_XFEREXT) {
696  switch_caller_extension_t *extension = NULL;
697 
698 
699  if ((extension = switch_caller_extension_new(session, "xferext", "xferext")) == 0) {
700  abort();
701  }
702 
703  for (hp = event->headers; hp; hp = hp->next) {
704  char *app;
705  char *data;
706 
707  if (!strcasecmp(hp->name, "application")) {
708  app = strdup(hp->value);
709  if (app) {
710  data = strchr(app, ' ');
711 
712  if (data) {
713  *data++ = '\0';
714  }
715 
716  switch_caller_extension_add_application(session, extension, app, data);
717  free(app);
718  }
719  }
720  }
721 
722  switch_channel_transfer_to_extension(channel, extension);
723 
724  } else if (cmd_hash == CMD_HANGUP) {
725  char *cause_name = switch_event_get_header(event, "hangup-cause");
727 
728  if (cause_name) {
729  cause = switch_channel_str2cause(cause_name);
730  }
731 
732  switch_channel_hangup(channel, cause);
733  } else if (cmd_hash == CMD_NOMEDIA) {
734  char *uuid = switch_event_get_header(event, "nomedia-uuid");
736  }
737 
738  status = SWITCH_STATUS_SUCCESS;
739 
740  done:
741 
743 
744  if (el) {
746  }
747 
748  if (elp) {
750  }
751 
752  return switch_channel_test_flag(channel, CF_BREAK) ? SWITCH_STATUS_BREAK : status;
753 }
switch_status_t switch_channel_set_variable_printf(switch_channel_t *channel, const char *varname, const char *fmt,...)
switch_time_t switch_micro_time_now(void)
Get the current epoch time in microseconds.
Definition: switch_time.c:310
#define switch_channel_hangup(channel, hangup_cause)
Hangup a channel flagging it's state machine to end.
void switch_channel_set_flag_recursive(switch_channel_t *channel, switch_channel_flag_t flag)
#define SWITCH_CHANNEL_SESSION_LOG(x)
An Abstract Representation of a dialplan extension.
const char * switch_channel_get_partner_uuid(switch_channel_t *channel)
switch_status_t switch_ivr_nomedia(const char *uuid, switch_media_flag_t flags)
Signal a session to request indirect media allowing it to exchange media directly with another device...
Definition: switch_ivr.c:1880
#define switch_channel_stop_broadcast(_channel)
switch_status_t switch_ivr_broadcast(const char *uuid, const char *path, switch_media_flag_t flags)
Signal the session to broadcast audio.
#define switch_channel_ready(_channel)
An event Header.
Definition: switch_event.h:65
#define switch_channel_media_ready(_channel)
static int switch_true(const char *expr)
Evaluate the truthfullness of a string expression.
Definition: switch_utils.h:450
uint32_t switch_channel_test_flag(switch_channel_t *channel, switch_channel_flag_t flag)
Test for presence of given flag on a given channel.
switch_status_t switch_core_session_read_frame(_In_ switch_core_session_t *session, switch_frame_t **frame, switch_io_flag_t flags, int stream_id)
Read a frame from a session.
#define zstr(x)
Definition: switch_utils.h:281
#define switch_core_session_execute_application(_a, _b, _c)
Execute an application on a session.
Definition: switch_core.h:1103
_Ret_ switch_channel_t * switch_core_session_get_channel(_In_ switch_core_session_t *session)
Retrieve a pointer to the channel object associated with a given session.
int64_t switch_time_t
Definition: switch_apr.h:188
#define switch_channel_audio_sync(_c)
const char * switch_channel_get_hold_music(switch_channel_t *channel)
static switch_bool_t switch_is_moh(const char *s)
Definition: switch_utils.h:286
char * switch_event_get_body(switch_event_t *event)
Retrieve the body value from an event.
Definition: switch_event.c:838
intptr_t switch_ssize_t
uint32_t switch_core_session_flush_private_events(switch_core_session_t *session)
Flush the private event queue of a session.
switch_call_cause_t switch_channel_str2cause(_In_ const char *str)
return a cause code for a given string
An abstraction of a data frame.
Definition: switch_frame.h:43
void switch_caller_extension_add_application(_In_ switch_core_session_t *session, _In_ switch_caller_extension_t *caller_extension, _In_z_ const char *application_name, _In_z_ const char *extra_data)
Add an application (instruction) to the given extension.
uint16_t switch_port_t
const char * switch_channel_get_hold_music_partner(switch_channel_t *channel)
hashtable_flag_t flags
switch_call_cause_t
switch_caller_extension_t * switch_caller_extension_new(_In_ switch_core_session_t *session, _In_z_ const char *extension_name, _In_z_ const char *extension_number)
Create a new extension with desired parameters.
void switch_core_session_rwunlock(_In_ switch_core_session_t *session)
Unlock a read or write lock on as given session.
#define switch_str_nil(s)
Make a null string a blank string instead.
Definition: switch_utils.h:903
switch_status_t switch_ivr_activate_unicast(switch_core_session_t *session, char *local_ip, switch_port_t local_port, char *remote_ip, switch_port_t remote_port, char *transport, char *flags)
Definition: switch_ivr.c:398
switch_status_t
Common return values.
struct switch_event_header * next
Definition: switch_event.h:76
#define switch_core_session_locate(uuid_str)
Locate a session based on it's uuid.
Definition: switch_core.h:916
unsigned int switch_hashfunc_default(const char *key, switch_ssize_t *klen)
Definition: switch_apr.c:120
void switch_channel_transfer_to_extension(switch_channel_t *channel, switch_caller_extension_t *caller_extension)
#define switch_event_get_header(_e, _h)
Definition: switch_event.h:172
#define switch_channel_set_flag(_c, _f)
#define switch_test_flag(obj, flag)
Test for the existance of a flag on an arbitary object.
Definition: switch_utils.h:624
void switch_channel_clear_flag_recursive(switch_channel_t *channel, switch_channel_flag_t flag)
void switch_log_printf(_In_ switch_text_channel_t channel, _In_z_ const char *file, _In_z_ const char *func, _In_ int line, _In_opt_z_ const char *userdata, _In_ switch_log_level_t level, _In_z_ _Printf_format_string_ const char *fmt,...) PRINTF_FUNCTION(7
Write log data to the logging engine.
#define switch_core_session_strdup(_session, _todup)
Copy a string using memory allocation from a session's pool.
Definition: switch_core.h:717
switch_status_t switch_channel_wait_for_flag(switch_channel_t *channel, switch_channel_flag_t want_flag, switch_bool_t pres, uint32_t to, switch_channel_t *super_channel)
void switch_channel_clear_flag(switch_channel_t *channel, switch_channel_flag_t flag)
Clear given flag(s) from a channel.
#define switch_channel_set_variable(_channel, _var, _val)
#define switch_core_session_kill_channel(session, sig)
Send a signal to a channel.
Definition: switch_core.h:1352
char * switch_channel_get_name(switch_channel_t *channel)
Retrieve the name of a given channel.
#define SWITCH_READ_ACCEPTABLE(status)
Definition: switch_utils.h:995
switch_event_header_t * headers
Definition: switch_event.h:90
switch_status_t switch_ivr_session_transfer ( switch_core_session_t session,
const char *  extension,
const char *  dialplan,
const char *  context 
)

Definition at line 2037 of file switch_ivr.c.

References CF_ORIGINATING, CF_TRANSFER, switch_caller_profile::context, CS_ROUTING, switch_caller_profile::destination_number, switch_caller_profile::dialplan, switch_core_session_message::from, switch_core_session_message::message_id, switch_caller_profile::pool, switch_caller_profile::rdnis, SMF_NONE, SWITCH_BRIDGE_VARIABLE, switch_caller_profile_clone(), SWITCH_CAUSE_BLIND_TRANSFER, SWITCH_CAUSE_EXCHANGE_ROUTING_ERROR, switch_channel_add_variable_var_check(), switch_channel_audio_sync, switch_channel_clear_flag(), switch_channel_clear_state_handler(), switch_channel_execute_on(), switch_channel_get_caller_profile(), switch_channel_get_name(), switch_channel_get_variable, switch_channel_hangup, SWITCH_CHANNEL_SESSION_LOG, switch_channel_set_caller_profile(), switch_channel_set_flag, switch_channel_set_state, switch_channel_set_variable, switch_channel_set_variable_var_check(), switch_core_session_get_channel(), switch_core_session_locate, switch_core_session_receive_message, switch_core_session_reset(), switch_core_session_rwunlock(), switch_core_session_sprintf(), switch_core_sprintf(), switch_core_strdup, switch_epoch_time_now(), SWITCH_FALSE, SWITCH_HANGUP_AFTER_BRIDGE_VARIABLE, switch_ivr_media(), SWITCH_LOG_NOTICE, switch_log_printf(), SWITCH_MAX_FORWARDS_VARIABLE, SWITCH_MAX_SESSION_TRANSFERS_VARIABLE, SWITCH_MESSAGE_INDICATE_TRANSFER, SWITCH_SIGNAL_BOND_VARIABLE, SWITCH_SIGNAL_BRIDGE_VARIABLE, SWITCH_STACK_PUSH, SWITCH_STATUS_FALSE, SWITCH_STATUS_SUCCESS, SWITCH_TEMP_HOLD_MUSIC_VARIABLE, SWITCH_TRANSFER_HISTORY_VARIABLE, SWITCH_TRANSFER_SOURCE_VARIABLE, SWITCH_TRUE, switch_caller_profile::transfer_source, switch_caller_profile::uuid_str, and zstr.

2039 {
2041  switch_caller_profile_t *profile, *new_profile;
2042  switch_core_session_message_t msg = { 0 };
2043  switch_core_session_t *other_session;
2044  switch_channel_t *other_channel = NULL;
2045  const char *uuid = NULL;
2046  const char *max_forwards;
2047  const char *forwardvar_name = SWITCH_MAX_SESSION_TRANSFERS_VARIABLE; /* max_session_transfers has first priority for setting maximum */
2048  const char *forwardvar = switch_channel_get_variable(channel, forwardvar_name);
2049  int forwardval = 70;
2050  const char *use_dialplan = dialplan, *use_context = context;
2051 
2052  if (zstr(forwardvar)) {
2053  forwardvar_name = SWITCH_MAX_FORWARDS_VARIABLE; /* fall back to max_forwards variable for setting maximum */
2054  forwardvar = switch_channel_get_variable(channel, forwardvar_name);
2055  }
2056  if (!zstr(forwardvar)) {
2057  forwardval = atoi(forwardvar) - 1;
2058  }
2059  if (forwardval <= 0) {
2061  return SWITCH_STATUS_FALSE;
2062  }
2063 
2064  max_forwards = switch_core_session_sprintf(session, "%d", forwardval);
2065  switch_channel_set_variable(channel, forwardvar_name, max_forwards);
2066 
2069 
2070  /* clear all state handlers */
2071  switch_channel_clear_state_handler(channel, NULL);
2072 
2073  /* reset temp hold music */
2075 
2076  switch_channel_execute_on(channel, "execute_on_blind_transfer");
2077 
2078  if ((profile = switch_channel_get_caller_profile(channel))) {
2079  const char *var;
2080 
2081  if (zstr(dialplan) && (var = switch_channel_get_variable(channel, "force_transfer_dialplan"))) {
2082  use_dialplan = var;
2083  }
2084 
2085  if (zstr(context) && (var = switch_channel_get_variable(channel, "force_transfer_context"))) {
2086  use_context = var;
2087  }
2088 
2089  if (zstr(use_dialplan)) {
2090  use_dialplan = profile->dialplan;
2091  if (!zstr(use_dialplan) && !strcasecmp(use_dialplan, "inline")) {
2092  use_dialplan = NULL;
2093  }
2094  }
2095 
2096  if (zstr(use_context)) {
2097  use_context = profile->context;
2098  }
2099 
2100  if (zstr(use_dialplan)) {
2101  use_dialplan = "XML";
2102  }
2103 
2104  if (zstr(use_context)) {
2105  use_context = "default";
2106  }
2107 
2108  if (zstr(extension)) {
2109  extension = "service";
2110  }
2111 
2112  new_profile = switch_caller_profile_clone(session, profile);
2113 
2114  new_profile->dialplan = switch_core_strdup(new_profile->pool, use_dialplan);
2115  new_profile->context = switch_core_strdup(new_profile->pool, use_context);
2116  new_profile->destination_number = switch_core_strdup(new_profile->pool, extension);
2117  new_profile->rdnis = switch_core_strdup(new_profile->pool, profile->destination_number);
2118 
2120 
2121  /* Set CF_TRANSFER flag before hanging up bleg to avoid race condition */
2123 
2124  /* If HANGUP_AFTER_BRIDGE is set to 'true', SWITCH_SIGNAL_BRIDGE_VARIABLE
2125  * will not have a value, so we need to check SWITCH_BRIDGE_VARIABLE */
2126 
2128 
2129  if (!uuid) {
2131  }
2132 
2133  if (uuid && (other_session = switch_core_session_locate(uuid))) {
2134  other_channel = switch_core_session_get_channel(other_session);
2136  switch_core_session_rwunlock(other_session);
2137  }
2138 
2140  && (other_session = switch_core_session_locate(uuid))) {
2141  other_channel = switch_core_session_get_channel(other_session);
2142 
2145 
2148 
2149  /* If we are transferring the CALLER out of the bridge, we do not want to hang up on them */
2151 
2153  switch_ivr_media(uuid, SMF_NONE);
2154 
2155  switch_core_session_rwunlock(other_session);
2156  }
2157 
2158  switch_channel_set_caller_profile(channel, new_profile);
2159 
2161  switch_channel_audio_sync(channel);
2162 
2164  msg.from = __FILE__;
2165  switch_core_session_receive_message(session, &msg);
2166 
2167  switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session), SWITCH_LOG_NOTICE, "Transfer %s to %s[%s@%s]\n", switch_channel_get_name(channel), use_dialplan,
2168  extension, use_context);
2169 
2170 
2171  new_profile->transfer_source = switch_core_sprintf(new_profile->pool, "%ld:%s:bl_xfer:%s/%s/%s",
2172  (long) switch_epoch_time_now(NULL), new_profile->uuid_str,
2173  extension, use_context, use_dialplan);
2176  return SWITCH_STATUS_SUCCESS;
2177  }
2178 
2179  return SWITCH_STATUS_FALSE;
2180 }
#define SWITCH_SIGNAL_BRIDGE_VARIABLE
Definition: switch_types.h:201
#define switch_channel_hangup(channel, hangup_cause)
Hangup a channel flagging it's state machine to end.
switch_status_t switch_channel_execute_on(switch_channel_t *channel, const char *variable_prefix)
char * switch_core_session_sprintf(_In_ switch_core_session_t *session, _In_z_ _Printf_format_string_ const char *fmt,...)
printf-style style printing routine. The data is output to a string allocated from the session ...
#define SWITCH_CHANNEL_SESSION_LOG(x)
Call Specific Data.
Definition: switch_caller.h:73
switch_core_session_message_types_t message_id
Definition: switch_core.h:181
void switch_core_session_reset(_In_ switch_core_session_t *session, switch_bool_t flush_dtmf, switch_bool_t reset_read_codec)
Reset the buffers and resampler on a session.
#define switch_channel_set_state(channel, state)
Set the current state of a channel.
#define SWITCH_TRANSFER_SOURCE_VARIABLE
Definition: switch_types.h:143
#define switch_core_strdup(_pool, _todup)
Copy a string using memory allocation from a given pool.
Definition: switch_core.h:729
switch_caller_profile_t * switch_caller_profile_clone(_In_ switch_core_session_t *session, _In_ switch_caller_profile_t *tocopy)
Clone an existing caller profile object.
void switch_channel_set_caller_profile(switch_channel_t *channel, switch_caller_profile_t *caller_profile)
Set the given channel's caller profile.
const char * dialplan
Definition: switch_caller.h:77
switch_status_t switch_ivr_media(const char *uuid, switch_media_flag_t flags)
Signal a session to request direct media access to it's remote end.
Definition: switch_ivr.c:1674
A message object designed to allow unlike technologies to exchange data.
Definition: switch_core.h:177
#define zstr(x)
Definition: switch_utils.h:281
_Ret_ switch_channel_t * switch_core_session_get_channel(_In_ switch_core_session_t *session)
Retrieve a pointer to the channel object associated with a given session.
#define SWITCH_HANGUP_AFTER_BRIDGE_VARIABLE
Definition: switch_types.h:216
#define switch_channel_audio_sync(_c)
switch_status_t switch_channel_add_variable_var_check(switch_channel_t *channel, const char *varname, const char *value, switch_bool_t var_check, switch_stack_t stack)
void switch_channel_clear_state_handler(switch_channel_t *channel, const switch_state_handler_table_t *state_handler)
clear a state handler table from a given channel
#define switch_channel_get_variable(_c, _v)
#define SWITCH_BRIDGE_VARIABLE
Definition: switch_types.h:199
#define switch_core_session_receive_message(_session, _message)
Definition: switch_core.h:1217
void switch_core_session_rwunlock(_In_ switch_core_session_t *session)
Unlock a read or write lock on as given session.
switch_status_t switch_channel_set_variable_var_check(switch_channel_t *channel, const char *varname, const char *value, switch_bool_t var_check)
#define SWITCH_SIGNAL_BOND_VARIABLE
Definition: switch_types.h:202
#define switch_core_session_locate(uuid_str)
Locate a session based on it's uuid.
Definition: switch_core.h:916
#define SWITCH_TEMP_HOLD_MUSIC_VARIABLE
Definition: switch_types.h:193
#define switch_channel_set_flag(_c, _f)
#define SWITCH_TRANSFER_HISTORY_VARIABLE
Definition: switch_types.h:142
time_t switch_epoch_time_now(time_t *t)
Get the current epoch time.
Definition: switch_time.c:321
void switch_log_printf(_In_ switch_text_channel_t channel, _In_z_ const char *file, _In_z_ const char *func, _In_ int line, _In_opt_z_ const char *userdata, _In_ switch_log_level_t level, _In_z_ _Printf_format_string_ const char *fmt,...) PRINTF_FUNCTION(7
Write log data to the logging engine.
#define SWITCH_MAX_SESSION_TRANSFERS_VARIABLE
Definition: switch_types.h:224
void switch_channel_clear_flag(switch_channel_t *channel, switch_channel_flag_t flag)
Clear given flag(s) from a channel.
char * switch_core_sprintf(_In_ switch_memory_pool_t *pool, _In_z_ _Printf_format_string_ const char *fmt,...)
printf-style style printing routine. The data is output to a string allocated from the pool ...
#define SWITCH_MAX_FORWARDS_VARIABLE
Definition: switch_types.h:223
#define switch_channel_set_variable(_channel, _var, _val)
switch_caller_profile_t * switch_channel_get_caller_profile(switch_channel_t *channel)
Retrieve the given channel's caller profile.
char * switch_channel_get_name(switch_channel_t *channel)
Retrieve the name of a given channel.
switch_memory_pool_t * pool
void switch_ivr_set_json_call_stats ( cJSON json,
switch_core_session_t session,
switch_media_type_t  type 
)

Definition at line 3076 of file switch_ivr.c.

References add_jstat, switch_rtp_numbers_t::burstrate, cJSON_AddItemToArray(), cJSON_AddItemToObject(), cJSON_CreateArray(), cJSON_CreateNumber(), cJSON_CreateObject(), switch_rtp_numbers_t::cng_packet_count, switch_rtp_numbers_t::dtmf_packet_count, ep, switch_rtp_numbers_t::error_log, switch_rtp_numbers_t::flaws, switch_rtp_numbers_t::flush_packet_count, switch_rtp_stats_t::inbound, switch_rtp_numbers_t::jb_packet_count, switch_rtp_numbers_t::largest_jb_size, switch_rtp_numbers_t::lossrate, switch_rtp_numbers_t::max_variance, switch_rtp_numbers_t::mean_interval, switch_rtp_numbers_t::media_bytes, switch_rtp_numbers_t::media_packet_count, switch_rtp_numbers_t::min_variance, switch_rtp_numbers_t::mos, error_period::next, switch_rtcp_numbers_t::octet_count, switch_rtp_stats_t::outbound, switch_rtp_numbers_t::packet_count, switch_rtcp_numbers_t::packet_count, switch_rtp_numbers_t::R, switch_rtp_numbers_t::raw_bytes, switch_rtp_stats_t::rtcp, switch_rtp_numbers_t::skip_packet_count, error_period::start, switch_rtp_numbers_t::std_deviation, error_period::stop, switch_core_media_get_stats(), SWITCH_MEDIA_TYPE_VIDEO, and switch_rtp_numbers_t::variance.

Referenced by switch_ivr_generate_json_cdr().

3077 {
3078  const char *name = (type == SWITCH_MEDIA_TYPE_VIDEO) ? "video" : "audio";
3079  cJSON *j_stat, *j_in, *j_out;
3080  switch_rtp_stats_t *stats = switch_core_media_get_stats(session, type, NULL);
3081  char var_val[35] = "";
3082 
3083  if (!stats) return;
3084 
3085  j_stat = cJSON_CreateObject();
3086  j_in = cJSON_CreateObject();
3087  j_out = cJSON_CreateObject();
3088 
3089  cJSON_AddItemToObject(json, name, j_stat);
3090  cJSON_AddItemToObject(j_stat, "inbound", j_in);
3091  cJSON_AddItemToObject(j_stat, "outbound", j_out);
3092 
3093  stats->inbound.std_deviation = sqrt(stats->inbound.variance);
3094 
3095  add_jstat(j_in, stats->inbound.raw_bytes, "raw_bytes");
3096  add_jstat(j_in, stats->inbound.media_bytes, "media_bytes");
3097  add_jstat(j_in, stats->inbound.packet_count, "packet_count");
3098  add_jstat(j_in, stats->inbound.media_packet_count, "media_packet_count");
3099  add_jstat(j_in, stats->inbound.skip_packet_count, "skip_packet_count");
3100  add_jstat(j_in, stats->inbound.jb_packet_count, "jitter_packet_count");
3101  add_jstat(j_in, stats->inbound.dtmf_packet_count, "dtmf_packet_count");
3102  add_jstat(j_in, stats->inbound.cng_packet_count, "cng_packet_count");
3103  add_jstat(j_in, stats->inbound.flush_packet_count, "flush_packet_count");
3104  add_jstat(j_in, stats->inbound.largest_jb_size, "largest_jb_size");
3105  add_jstat(j_in, stats->inbound.min_variance, "jitter_min_variance");
3106  add_jstat(j_in, stats->inbound.max_variance, "jitter_max_variance");
3107  add_jstat(j_in, stats->inbound.lossrate, "jitter_loss_rate");
3108  add_jstat(j_in, stats->inbound.burstrate, "jitter_burst_rate");
3109  add_jstat(j_in, stats->inbound.mean_interval, "mean_interval");
3110  add_jstat(j_in, stats->inbound.flaws, "flaw_total");
3111  add_jstat(j_in, stats->inbound.R, "quality_percentage");
3112  add_jstat(j_in, stats->inbound.mos, "mos");
3113 
3114 
3115  if (stats->inbound.error_log) {
3116  cJSON *j_err_log, *j_err;
3118 
3119  j_err_log = cJSON_CreateArray();
3120  cJSON_AddItemToObject(j_in, "errorLog", j_err_log);
3121 
3122  for(ep = stats->inbound.error_log; ep; ep = ep->next) {
3123 
3124  if (!(ep->start && ep->stop)) continue;
3125 
3126  j_err = cJSON_CreateObject();
3127 
3128  cJSON_AddItemToObject(j_err, "start", cJSON_CreateNumber(ep->start));
3129  cJSON_AddItemToObject(j_err, "stop", cJSON_CreateNumber(ep->stop));
3130  cJSON_AddItemToObject(j_err, "durationMS", cJSON_CreateNumber((ep->stop - ep->start) / 1000));
3131  cJSON_AddItemToArray(j_err_log, j_err);
3132  }
3133  }
3134 
3135  add_jstat(j_out, stats->outbound.raw_bytes, "raw_bytes");
3136  add_jstat(j_out, stats->outbound.media_bytes, "media_bytes");
3137  add_jstat(j_out, stats->outbound.packet_count, "packet_count");
3138  add_jstat(j_out, stats->outbound.media_packet_count, "media_packet_count");
3139  add_jstat(j_out, stats->outbound.skip_packet_count, "skip_packet_count");
3140  add_jstat(j_out, stats->outbound.dtmf_packet_count, "dtmf_packet_count");
3141  add_jstat(j_out, stats->outbound.cng_packet_count, "cng_packet_count");
3142  add_jstat(j_out, stats->rtcp.packet_count, "rtcp_packet_count");
3143  add_jstat(j_out, stats->rtcp.octet_count, "rtcp_octet_count");
3144 }
cJSON * cJSON_CreateObject(void)
Definition: switch_json.c:544
switch_size_t flaws
Definition: switch_types.h:657
cJSON * cJSON_CreateNumber(double num)
Definition: switch_json.c:541
switch_rtp_numbers_t inbound
Definition: switch_types.h:690
switch_rtp_stats_t * switch_core_media_get_stats(switch_core_session_t *session, switch_media_type_t type, switch_memory_pool_t *pool)
switch_size_t largest_jb_size
Definition: switch_types.h:637
struct error_period * next
Definition: switch_types.h:622
switch_size_t media_bytes
Definition: switch_types.h:628
switch_size_t dtmf_packet_count
Definition: switch_types.h:634
switch_rtcp_numbers_t rtcp
Definition: switch_types.h:692
int64_t stop
Definition: switch_types.h:621
switch_size_t raw_bytes
Definition: switch_types.h:627
void cJSON_AddItemToArray(cJSON *array, cJSON *item)
Definition: switch_json.c:519
switch_rtp_numbers_t outbound
Definition: switch_types.h:691
void cJSON_AddItemToObject(cJSON *object, const char *string, cJSON *item)
Definition: switch_json.c:520
int64_t start
Definition: switch_types.h:620
switch_size_t packet_count
Definition: switch_types.h:629
switch_size_t jb_packet_count
Definition: switch_types.h:633
switch_size_t skip_packet_count
Definition: switch_types.h:632
static const char * ep
Definition: switch_json.c:36
struct error_period * error_log
Definition: switch_types.h:661
switch_size_t flush_packet_count
Definition: switch_types.h:636
switch_size_t media_packet_count
Definition: switch_types.h:631
cJSON * cJSON_CreateArray(void)
Definition: switch_json.c:543
switch_size_t cng_packet_count
Definition: switch_types.h:635
#define add_jstat(_j, _i, _s)
Definition: switch_ivr.c:3072
static void switch_ivr_set_json_chan_vars ( cJSON json,
switch_channel_t channel,
switch_bool_t  urlencode 
)
static

Definition at line 3146 of file switch_ivr.c.

References cJSON_AddItemToObject(), cJSON_CreateString(), memset(), switch_event_header::name, switch_event_header::next, switch_channel_variable_first(), switch_channel_variable_last(), switch_safe_free, switch_url_encode(), switch_event_header::value, and zstr.

Referenced by switch_ivr_generate_json_cdr().

3147 {
3149 
3150  if (!hi)
3151  return;
3152 
3153  for (; hi; hi = hi->next) {
3154  if (!zstr(hi->name) && !zstr(hi->value)) {
3155  char *data = hi->value;
3156  if (urlencode) {
3157  switch_size_t dlen = strlen(hi->value) * 3;
3158 
3159  if ((data = malloc(dlen))) {
3160  memset(data, 0, dlen);
3161  switch_url_encode(hi->value, data, dlen);
3162  }
3163  }
3164 
3165  cJSON_AddItemToObject(json, hi->name, cJSON_CreateString(data));
3166 
3167  if (data != hi->value) {
3168  switch_safe_free(data);
3169  }
3170  }
3171  }
3173 }
An event Header.
Definition: switch_event.h:65
char * switch_url_encode(const char *url, char *buf, size_t len)
switch_event_header_t * switch_channel_variable_first(switch_channel_t *channel)
Start iterating over the entries in the channel variable list.
#define zstr(x)
Definition: switch_utils.h:281
#define switch_safe_free(it)
Free a pointer and set it to NULL unless it already is NULL.
Definition: switch_utils.h:789
uintptr_t switch_size_t
void cJSON_AddItemToObject(cJSON *object, const char *string, cJSON *item)
Definition: switch_json.c:520
cJSON * cJSON_CreateString(const char *string)
Definition: switch_json.c:542
struct switch_event_header * next
Definition: switch_event.h:76
void switch_channel_variable_last(switch_channel_t *channel)
Stop iterating over channel variables.
memset(buf, 0, buflen)
static void switch_ivr_set_json_profile_data ( cJSON json,
switch_caller_profile_t caller_profile 
)
static

Definition at line 3055 of file switch_ivr.c.

References switch_caller_profile::ani, switch_caller_profile::aniii, switch_caller_profile::caller_id_name, switch_caller_profile::caller_id_number, switch_caller_profile::chan_name, cJSON_AddItemToObject(), cJSON_CreateString(), switch_caller_profile::context, switch_caller_profile::destination_number, switch_caller_profile::dialplan, switch_caller_profile::network_addr, switch_caller_profile::rdnis, switch_caller_profile::source, switch_caller_profile::username, and switch_caller_profile::uuid.

Referenced by switch_ivr_generate_json_cdr().

3056 {
3057  cJSON_AddItemToObject(json, "username", cJSON_CreateString((char *)caller_profile->username));
3058  cJSON_AddItemToObject(json, "dialplan", cJSON_CreateString((char *)caller_profile->dialplan));
3059  cJSON_AddItemToObject(json, "caller_id_name", cJSON_CreateString((char *)caller_profile->caller_id_name));
3060  cJSON_AddItemToObject(json, "ani", cJSON_CreateString((char *)caller_profile->ani));
3061  cJSON_AddItemToObject(json, "aniii", cJSON_CreateString((char *)caller_profile->aniii));
3062  cJSON_AddItemToObject(json, "caller_id_number", cJSON_CreateString((char *)caller_profile->caller_id_number));
3063  cJSON_AddItemToObject(json, "network_addr", cJSON_CreateString((char *)caller_profile->network_addr));
3064  cJSON_AddItemToObject(json, "rdnis", cJSON_CreateString((char *)caller_profile->rdnis));
3065  cJSON_AddItemToObject(json, "destination_number", cJSON_CreateString(caller_profile->destination_number));
3066  cJSON_AddItemToObject(json, "uuid", cJSON_CreateString(caller_profile->uuid));
3067  cJSON_AddItemToObject(json, "source", cJSON_CreateString((char *)caller_profile->source));
3068  cJSON_AddItemToObject(json, "context", cJSON_CreateString((char *)caller_profile->context));
3069  cJSON_AddItemToObject(json, "chan_name", cJSON_CreateString(caller_profile->chan_name));
3070 }
const char * network_addr
Definition: switch_caller.h:93
const char * dialplan
Definition: switch_caller.h:77
const char * username
Definition: switch_caller.h:75
const char * caller_id_name
Definition: switch_caller.h:79
void cJSON_AddItemToObject(cJSON *object, const char *string, cJSON *item)
Definition: switch_json.c:520
cJSON * cJSON_CreateString(const char *string)
Definition: switch_json.c:542
const char * caller_id_number
Definition: switch_caller.h:81
int switch_ivr_set_xml_call_stats ( switch_xml_t  xml,
switch_core_session_t session,
int  off,
switch_media_type_t  type 
)

Definition at line 2579 of file switch_ivr.c.

References add_stat, add_stat_double, switch_rtp_numbers_t::burstrate, switch_rtp_numbers_t::cng_packet_count, switch_rtp_numbers_t::dtmf_packet_count, ep, switch_rtp_numbers_t::error_log, switch_rtp_numbers_t::flaws, switch_rtp_numbers_t::flush_packet_count, switch_rtp_stats_t::inbound, switch_rtp_numbers_t::jb_packet_count, switch_rtp_numbers_t::largest_jb_size, switch_rtp_numbers_t::lossrate, switch_rtp_numbers_t::max_variance, switch_rtp_numbers_t::mean_interval, switch_rtp_numbers_t::media_bytes, switch_rtp_numbers_t::media_packet_count, switch_rtp_numbers_t::min_variance, switch_rtp_numbers_t::mos, error_period::next, switch_rtcp_numbers_t::octet_count, switch_rtp_stats_t::outbound, switch_rtp_numbers_t::packet_count, switch_rtcp_numbers_t::packet_count, switch_rtp_numbers_t::R, switch_rtp_numbers_t::raw_bytes, switch_rtp_stats_t::rtcp, switch_rtp_numbers_t::skip_packet_count, error_period::start, switch_rtp_numbers_t::std_deviation, error_period::stop, switch_core_media_get_stats(), SWITCH_MEDIA_TYPE_VIDEO, switch_snprintf(), SWITCH_TIME_T_FMT, switch_xml_add_child_d, switch_xml_set_txt_d, and switch_rtp_numbers_t::variance.

Referenced by switch_ivr_generate_xml_cdr().

2580 {
2581  const char *name = (type == SWITCH_MEDIA_TYPE_VIDEO) ? "video" : "audio";
2582  switch_xml_t x_stat, x_in, x_out, x_tmp = NULL;
2583  int loff = 0;
2584  switch_rtp_stats_t *stats = switch_core_media_get_stats(session, type, NULL);
2585  char var_val[35] = "";
2586 
2587  if (!stats) return off;
2588 
2589  if (!(x_stat = switch_xml_add_child_d(xml, name, off++))) {
2590  abort();
2591  }
2592 
2593  if (!(x_in = switch_xml_add_child_d(x_stat, "inbound", off++))) {
2594  abort();
2595  }
2596 
2597  if (!(x_out = switch_xml_add_child_d(x_stat, "outbound", off++))) {
2598  abort();
2599  }
2600 
2601  stats->inbound.std_deviation = sqrt(stats->inbound.variance);
2602 
2603  add_stat(x_in, stats->inbound.raw_bytes, "raw_bytes");
2604  add_stat(x_in, stats->inbound.media_bytes, "media_bytes");
2605  add_stat(x_in, stats->inbound.packet_count, "packet_count");
2606  add_stat(x_in, stats->inbound.media_packet_count, "media_packet_count");
2607  add_stat(x_in, stats->inbound.skip_packet_count, "skip_packet_count");
2608  add_stat(x_in, stats->inbound.jb_packet_count, "jitter_packet_count");
2609  add_stat(x_in, stats->inbound.dtmf_packet_count, "dtmf_packet_count");
2610  add_stat(x_in, stats->inbound.cng_packet_count, "cng_packet_count");
2611  add_stat(x_in, stats->inbound.flush_packet_count, "flush_packet_count");
2612  add_stat(x_in, stats->inbound.largest_jb_size, "largest_jb_size");
2613  add_stat_double(x_in, stats->inbound.min_variance, "jitter_min_variance");
2614  add_stat_double(x_in, stats->inbound.max_variance, "jitter_max_variance");
2615  add_stat_double(x_in, stats->inbound.lossrate, "jitter_loss_rate");
2616  add_stat_double(x_in, stats->inbound.burstrate, "jitter_burst_rate");
2617  add_stat_double(x_in, stats->inbound.mean_interval, "mean_interval");
2618  add_stat(x_in, stats->inbound.flaws, "flaw_total");
2619  add_stat_double(x_in, stats->inbound.R, "quality_percentage");
2620  add_stat_double(x_in, stats->inbound.mos, "mos");
2621 
2622 
2623  if (stats->inbound.error_log) {
2624  switch_xml_t x_err_log, x_err;
2626  int eoff = 0;
2627 
2628  if (!(x_err_log = switch_xml_add_child_d(x_stat, "error-log", off++))) {
2629  abort();
2630  }
2631 
2632  for(ep = stats->inbound.error_log; ep; ep = ep->next) {
2633 
2634  if (!(ep->start && ep->stop)) continue;
2635 
2636  if (!(x_err = switch_xml_add_child_d(x_err_log, "error-period", eoff++))) {
2637  abort();
2638  }
2639 
2640  switch_snprintf(var_val, sizeof(var_val), "%" SWITCH_TIME_T_FMT, ep->start);
2641  x_tmp = switch_xml_add_child_d(x_err, "start", 0);
2642  switch_xml_set_txt_d(x_tmp, var_val);
2643 
2644  switch_snprintf(var_val, sizeof(var_val), "%" SWITCH_TIME_T_FMT, ep->stop);
2645  x_tmp = switch_xml_add_child_d(x_err, "stop", 1);
2646  switch_xml_set_txt_d(x_tmp, var_val);
2647 
2648  switch_snprintf(var_val, sizeof(var_val), "%" SWITCH_TIME_T_FMT, (ep->stop - ep->start) / 1000);
2649  x_tmp = switch_xml_add_child_d(x_err, "duration-msec", 2);
2650  switch_xml_set_txt_d(x_tmp, var_val);
2651  }
2652  }
2653 
2654  add_stat(x_out, stats->outbound.raw_bytes, "raw_bytes");
2655  add_stat(x_out, stats->outbound.media_bytes, "media_bytes");
2656  add_stat(x_out, stats->outbound.packet_count, "packet_count");
2657  add_stat(x_out, stats->outbound.media_packet_count, "media_packet_count");
2658  add_stat(x_out, stats->outbound.skip_packet_count, "skip_packet_count");
2659  add_stat(x_out, stats->outbound.dtmf_packet_count, "dtmf_packet_count");
2660  add_stat(x_out, stats->outbound.cng_packet_count, "cng_packet_count");
2661  add_stat(x_out, stats->rtcp.packet_count, "rtcp_packet_count");
2662  add_stat(x_out, stats->rtcp.octet_count, "rtcp_octet_count");
2663 
2664  return off;
2665 }
switch_size_t flaws
Definition: switch_types.h:657
switch_rtp_numbers_t inbound
Definition: switch_types.h:690
switch_rtp_stats_t * switch_core_media_get_stats(switch_core_session_t *session, switch_media_type_t type, switch_memory_pool_t *pool)
switch_size_t largest_jb_size
Definition: switch_types.h:637
struct error_period * next
Definition: switch_types.h:622
#define switch_xml_add_child_d(xml, name, off)
wrapper for switch_xml_add_child() that strdup()s name
Definition: switch_xml.h:269
A representation of an XML tree.
Definition: switch_xml.h:76
switch_size_t media_bytes
Definition: switch_types.h:628
switch_size_t dtmf_packet_count
Definition: switch_types.h:634
int switch_snprintf(_Out_z_cap_(len) char *buf, _In_ switch_size_t len, _In_z_ _Printf_format_string_ const char *format,...)
switch_rtcp_numbers_t rtcp
Definition: switch_types.h:692
int64_t stop
Definition: switch_types.h:621
switch_size_t raw_bytes
Definition: switch_types.h:627
#define add_stat(_x, _i, _s)
Definition: switch_ivr.c:2569
switch_rtp_numbers_t outbound
Definition: switch_types.h:691
#define SWITCH_TIME_T_FMT
int64_t start
Definition: switch_types.h:620
switch_size_t packet_count
Definition: switch_types.h:629
#define add_stat_double(_x, _i, _s)
Definition: switch_ivr.c:2574
switch_size_t jb_packet_count
Definition: switch_types.h:633
switch_size_t skip_packet_count
Definition: switch_types.h:632
static const char * ep
Definition: switch_json.c:36
struct error_period * error_log
Definition: switch_types.h:661
switch_size_t flush_packet_count
Definition: switch_types.h:636
#define switch_xml_set_txt_d(xml, txt)
wrapper for switch_xml_set_txt() that strdup()s txt \ sets the character content for the given tag an...
Definition: switch_xml.h:283
switch_size_t media_packet_count
Definition: switch_types.h:631
switch_size_t cng_packet_count
Definition: switch_types.h:635
static int switch_ivr_set_xml_chan_var ( switch_xml_t  xml,
const char *  var,
const char *  val,
int  off 
)
static

Definition at line 2667 of file switch_ivr.c.

References memset(), switch_url_encode(), switch_xml_add_child_d, switch_xml_set_txt_d, and zstr.

Referenced by switch_ivr_set_xml_chan_vars().

2668 {
2669  char *data;
2670  switch_size_t dlen = strlen(val) * 3 + 1;
2671  switch_xml_t variable;
2672 
2673  if (!val) val = "";
2674 
2675  if (!zstr(var) && ((variable = switch_xml_add_child_d(xml, var, off++)))) {
2676  if ((data = malloc(dlen))) {
2677  memset(data, 0, dlen);
2678  switch_url_encode(val, data, dlen);
2679  switch_xml_set_txt_d(variable, data);
2680  free(data);
2681  } else abort();
2682  }
2683 
2684  return off;
2685 
2686 }
#define switch_xml_add_child_d(xml, name, off)
wrapper for switch_xml_add_child() that strdup()s name
Definition: switch_xml.h:269
A representation of an XML tree.
Definition: switch_xml.h:76
char * switch_url_encode(const char *url, char *buf, size_t len)
#define zstr(x)
Definition: switch_utils.h:281
uintptr_t switch_size_t
#define switch_xml_set_txt_d(xml, txt)
wrapper for switch_xml_set_txt() that strdup()s txt \ sets the character content for the given tag an...
Definition: switch_xml.h:283
memset(buf, 0, buflen)
static void unicast_thread_launch ( switch_unicast_conninfo_t conninfo)
static

Definition at line 355 of file switch_ivr.c.

References switch_unicast_conninfo::session, SUF_THREAD_RUNNING, switch_core_session_get_pool(), switch_set_flag_locked, switch_thread_create(), SWITCH_THREAD_STACKSIZE, switch_threadattr_create(), switch_threadattr_stacksize_set(), switch_unicast_conninfo::thread, and unicast_thread_run().

Referenced by switch_ivr_park().

356 {
357  switch_threadattr_t *thd_attr = NULL;
358 
362  switch_thread_create(&conninfo->thread, thd_attr, unicast_thread_run, conninfo, switch_core_session_get_pool(conninfo->session));
363 }
switch_status_t switch_threadattr_stacksize_set(switch_threadattr_t *attr, switch_size_t stacksize)
Definition: switch_apr.c:660
#define SWITCH_THREAD_STACKSIZE
Definition: switch_types.h:551
#define switch_set_flag_locked(obj, flag)
Set a flag on an arbitrary object while locked.
Definition: switch_utils.h:638
switch_thread_t * thread
Definition: switch_ivr.h:64
switch_core_session_t * session
Definition: switch_ivr.h:48
switch_status_t switch_threadattr_create(switch_threadattr_t **new_attr, switch_memory_pool_t *pool)
Definition: switch_apr.c:642
switch_status_t switch_thread_create(switch_thread_t **new_thread, switch_threadattr_t *attr, switch_thread_start_t func, void *data, switch_memory_pool_t *cont)
Definition: switch_apr.c:675
switch_memory_pool_t * switch_core_session_get_pool(_In_ switch_core_session_t *session)
Retrieve the memory pool from a session.
static void *SWITCH_THREAD_FUNC unicast_thread_run(switch_thread_t *thread, void *obj)
Definition: switch_ivr.c:330
static void* SWITCH_THREAD_FUNC unicast_thread_run ( switch_thread_t thread,
void *  obj 
)
static

Definition at line 330 of file switch_ivr.c.

References switch_frame::buflen, switch_frame::data, switch_frame::datalen, switch_frame::samples, switch_unicast_conninfo::session, switch_unicast_conninfo::socket, switch_unicast_conninfo::stream_id, SUF_READY, SUF_THREAD_RUNNING, switch_clear_flag_locked, switch_core_session_write_frame(), SWITCH_IO_FLAG_NONE, switch_socket_recv(), SWITCH_STATUS_SUCCESS, switch_test_flag, and switch_unicast_conninfo::write_frame.

Referenced by unicast_thread_launch().

331 {
333  switch_size_t len;
334 
335  if (!conninfo) {
336  return NULL;
337  }
338 
339  while (switch_test_flag(conninfo, SUF_READY) && switch_test_flag(conninfo, SUF_THREAD_RUNNING)) {
340  len = conninfo->write_frame.buflen;
341  if (switch_socket_recv(conninfo->socket, conninfo->write_frame.data, &len) != SWITCH_STATUS_SUCCESS || len == 0) {
342  break;
343  }
344  conninfo->write_frame.datalen = (uint32_t) len;
345  conninfo->write_frame.samples = conninfo->write_frame.datalen / 2;
347  }
348 
351 
352  return NULL;
353 }
switch_socket_t * socket
Definition: switch_ivr.h:52
switch_status_t switch_socket_recv(switch_socket_t *sock, char *buf, switch_size_t *len)
Definition: switch_apr.c:782
switch_status_t switch_core_session_write_frame(_In_ switch_core_session_t *session, switch_frame_t *frame, switch_io_flag_t flags, int stream_id)
Write a frame to a session.
uint32_t buflen
Definition: switch_frame.h:59
uint32_t datalen
Definition: switch_frame.h:57
uintptr_t switch_size_t
switch_frame_t write_frame
Definition: switch_ivr.h:50
#define switch_clear_flag_locked(obj, flag)
Clear a flag on an arbitrary object.
Definition: switch_utils.h:648
uint32_t samples
Definition: switch_frame.h:61
switch_core_session_t * session
Definition: switch_ivr.h:48
#define switch_test_flag(obj, flag)
Test for the existance of a flag on an arbitary object.
Definition: switch_utils.h:624