Author: greenlizard Date: Tue Jun 12 15:20:17 2007 New Revision: 5311 Added: freeswitch/branches/greenlizard/build/config/ODBC.m4 - copied unchanged from r5310, /freeswitch/trunk/build/config/ODBC.m4 Modified: freeswitch/branches/greenlizard/conf/conference.conf.xml freeswitch/branches/greenlizard/conf/default_context.xml freeswitch/branches/greenlizard/conf/sofia.conf.xml freeswitch/branches/greenlizard/src/include/switch_module_interfaces.h freeswitch/branches/greenlizard/src/include/switch_types.h freeswitch/branches/greenlizard/src/mod/applications/mod_conference/mod_conference.c freeswitch/branches/greenlizard/src/mod/codecs/mod_g722/mod_g722.c freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/mod_sofia.c freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/mod_sofia.h freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia.c freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia_glue.c freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia_reg.c freeswitch/branches/greenlizard/src/mod/formats/mod_shout/mod_shout.c freeswitch/branches/greenlizard/src/mod/languages/mod_spidermonkey/mod_spidermonkey.c freeswitch/branches/greenlizard/src/switch_channel.c freeswitch/branches/greenlizard/src/switch_core.c freeswitch/branches/greenlizard/src/switch_cpp.cpp freeswitch/branches/greenlizard/src/switch_ivr_play_say.c freeswitch/branches/greenlizard/src/switch_rtp.c Log: merge changes from trunk version 5295 to 5309 Modified: freeswitch/branches/greenlizard/conf/conference.conf.xml ============================================================================== --- freeswitch/branches/greenlizard/conf/conference.conf.xml (original) +++ freeswitch/branches/greenlizard/conf/conference.conf.xml Tue Jun 12 15:20:17 2007 @@ -62,6 +62,8 @@ <!--<param name="unmuted-sound" value="unmuted.wav"/>--> <!-- File to play if you are alone in the conference --> <!--<param name="alone-sound" value="yactopitc.wav"/>--> + <!-- File to play endlessly (nobody will ever be able to talk) --> + <!--<param name="perpetual-sound" value="music.wav"/>--> <!-- File to play when you join the conference --> <!--<param name="enter-sound" value="welcome.wav"/>--> <!-- File to play when you leave the conference --> Modified: freeswitch/branches/greenlizard/conf/default_context.xml ============================================================================== --- freeswitch/branches/greenlizard/conf/default_context.xml (original) +++ freeswitch/branches/greenlizard/conf/default_context.xml Tue Jun 12 15:20:17 2007 @@ -19,6 +19,35 @@ </condition> </extension> + <extension name="9192"> + <condition field="destination_number" expression="^9192$"> + <!-- Maintain Buffer of 128k of audio (default is 64k) --> + <action application="set" data="stream_prebuffer=131072"/> + <!-- Play a stream --> + <action application="playback" data="shout://mp3.ihets.org/wfyihd132"/> + </condition> + </extension> + + + <!-- Example extension for require auth per-call. --> + <extension name="9191"> + <!-- Match the destination digits of 9191 --> + <condition field="destination_number" expression="^9191$"/> + <!-- Make sure the sip_authorized variable is set (set on all authed calls) + If it isn't, then send an auth challange. + --> + <condition field="${sip_authorized}" expression="true"> + <anti-action application="reject" data="407"/> + </condition> + + <!-- If you made it here all is well and the call is authed. + Do whatever you wish. + --> + <condition> + <action application="playback" data="/tmp/itworked.wav"/> + </condition> + </extension> + <extension name="tollfree"> <condition field="destination_number" expression="^(18(0{2}|8{2}|7{2}|6{2})\d{7})$"> <action application="enum" data="$1"/> Modified: freeswitch/branches/greenlizard/conf/sofia.conf.xml ============================================================================== --- freeswitch/branches/greenlizard/conf/sofia.conf.xml (original) +++ freeswitch/branches/greenlizard/conf/sofia.conf.xml Tue Jun 12 15:20:17 2007 @@ -50,6 +50,8 @@ <param name="rtp-timer-name" value="soft"/> <param name="rtp-ip" value="$${bind_server_ip}"/> <param name="sip-ip" value="$${bind_server_ip}"/> + <!--set to 'greedy' if you want your codec list to take precedence --> + <param name="inbound-codec-negotiation" value="generous"/> <!-- if you want to send any special bind params of your own --> <!--<param name="bind-params" value="transport=udp"/>--> Modified: freeswitch/branches/greenlizard/src/include/switch_module_interfaces.h ============================================================================== --- freeswitch/branches/greenlizard/src/include/switch_module_interfaces.h (original) +++ freeswitch/branches/greenlizard/src/include/switch_module_interfaces.h Tue Jun 12 15:20:17 2007 @@ -221,6 +221,8 @@ int speed; /*! the handle's memory pool */ switch_memory_pool_t *memory_pool; + /*! pre-buffer x bytes for streams */ + uint32_t prebuf; /*! private data for the format module to store handle specific info */ void *private_info; char *handler; Modified: freeswitch/branches/greenlizard/src/include/switch_types.h ============================================================================== --- freeswitch/branches/greenlizard/src/include/switch_types.h (original) +++ freeswitch/branches/greenlizard/src/include/switch_types.h Tue Jun 12 15:20:17 2007 @@ -957,7 +957,8 @@ SWITCH_CAUSE_MANAGER_REQUEST = 503, SWITCH_CAUSE_BLIND_TRANSFER = 600, SWITCH_CAUSE_ATTENDED_TRANSFER = 601, - SWITCH_CAUSE_ALLOTTED_TIMEOUT = 602 + SWITCH_CAUSE_ALLOTTED_TIMEOUT = 602, + SWITCH_CAUSE_USER_CHALLENGE = 603 } switch_call_cause_t; typedef enum { Modified: freeswitch/branches/greenlizard/src/mod/applications/mod_conference/mod_conference.c ============================================================================== --- freeswitch/branches/greenlizard/src/mod/applications/mod_conference/mod_conference.c (original) +++ freeswitch/branches/greenlizard/src/mod/applications/mod_conference/mod_conference.c Tue Jun 12 15:20:17 2007 @@ -175,6 +175,7 @@ char *enter_sound; char *exit_sound; char *alone_sound; + char *perpetual_sound; char *ack_sound; char *nack_sound; char *muted_sound; @@ -516,7 +517,7 @@ if (conference->count >= conference->anounce_count && conference->anounce_count > 1) { snprintf(msg, sizeof(msg), "There are %d callers", conference->count); conference_member_say(member, msg, CONF_DEFAULT_LEADIN); - } else if (conference->count == 1) { + } else if (conference->count == 1 && !conference->perpetual_sound) { if (conference->alone_sound) { conference_play_file(conference, conference->alone_sound, CONF_DEFAULT_LEADIN, switch_core_session_get_channel(member->session), 0); } else { @@ -684,6 +685,10 @@ switch_size_t file_data_len = samples * 2; int has_file_data = 0; + if (conference->perpetual_sound && !conference->fnode) { + conference_play_file(conference, conference->perpetual_sound, CONF_DEFAULT_LEADIN, NULL, 0); + } + /* Sync the conference to a single timing source */ if (switch_core_timer_next(&timer) != SWITCH_STATUS_SUCCESS) { switch_set_flag(conference, CFLAG_DESTRUCT); @@ -1479,6 +1484,7 @@ uint32_t interval = read_codec->implementation->microseconds_per_frame / 1000; uint32_t csamples = switch_bytes_per_frame(member->conference->rate, member->conference->interval); uint32_t samples = switch_bytes_per_frame(member->conference->rate, interval); + uint32_t tsamples = switch_bytes_per_frame(read_codec->implementation->samples_per_second, interval); uint32_t low_count = 0, bytes = samples * 2; call_list_t *call_list = NULL, *cp = NULL; @@ -1489,9 +1495,9 @@ if (switch_core_timer_init(&timer, member->conference->timer_name, interval, //member->conference->interval, - samples, NULL) == SWITCH_STATUS_SUCCESS) { + tsamples, NULL) == SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "setup timer %s success interval: %u samples: %u\n", - member->conference->timer_name, interval, samples); + member->conference->timer_name, interval, tsamples); } else { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Timer Setup Failed. Conference Cannot Start\n"); return; @@ -4536,6 +4542,7 @@ char *caller_id_number = NULL; char *caller_controls = NULL; char *member_flags = NULL; + char *perpetual_sound = NULL; uint32_t max_members = 0; uint32_t anounce_count = 0; char *maxmember_sound = NULL; @@ -4583,6 +4590,8 @@ exit_sound = val; } else if (!strcasecmp(var, "alone-sound")) { alone_sound = val; + } else if (!strcasecmp(var, "perpetual-sound")) { + perpetual_sound = val; } else if (!strcasecmp(var, "ack-sound")) { ack_sound = val; } else if (!strcasecmp(var, "nack-sound")) { @@ -4696,7 +4705,13 @@ conference->caller_id_name = switch_core_strdup(conference->pool, caller_id_name); conference->caller_id_number = switch_core_strdup(conference->pool, caller_id_number); - conference->mflags = MFLAG_CAN_SPEAK | MFLAG_CAN_HEAR; + + if (!switch_strlen_zero(perpetual_sound)) { + conference->perpetual_sound = switch_core_strdup(conference->pool, perpetual_sound); + conference->mflags = MFLAG_CAN_HEAR; + } else { + conference->mflags = MFLAG_CAN_SPEAK | MFLAG_CAN_HEAR; + } if (member_flags) { set_mflags(member_flags, &conference->mflags); Modified: freeswitch/branches/greenlizard/src/mod/codecs/mod_g722/mod_g722.c ============================================================================== --- freeswitch/branches/greenlizard/src/mod/codecs/mod_g722/mod_g722.c (original) +++ freeswitch/branches/greenlizard/src/mod/codecs/mod_g722/mod_g722.c Tue Jun 12 15:20:17 2007 @@ -142,10 +142,10 @@ /*.ianacode */ 9, /*.iananame */ "G722", /*.fmtp */ NULL, - /*.samples_per_second */ 16000, + /*.samples_per_second */ 8000, /*.bits_per_second */ 64000, /*.microseconds_per_frame */ 20000, - /*.samples_per_frame */ 320, + /*.samples_per_frame */ 160, /*.bytes_per_frame */ 640, /*.encoded_bytes_per_frame */ 160, /*.number_of_channels */ 1, Modified: freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/mod_sofia.c ============================================================================== --- freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/mod_sofia.c (original) +++ freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/mod_sofia.c Tue Jun 12 15:20:17 2007 @@ -806,17 +806,21 @@ case SWITCH_MESSAGE_INDICATE_REJECT: if (msg->string_arg) { int code = 0; - char *reason; + char *reason = NULL; if (switch_channel_test_flag(channel, CF_ANSWERED)) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_NOTICE, "Call is already answered, Rejecting with hangup\n"); switch_channel_hangup(channel, SWITCH_CAUSE_CALL_REJECTED); } else { - if ((reason = strchr(msg->string_arg, ' '))) { - reason++; + if (!switch_strlen_zero(msg->string_arg)){ code = atoi(msg->string_arg); - } else { + if ((reason = strchr(msg->string_arg, ' '))) { + reason++; + } + } + + if (!reason && code != 407) { reason = "Call Refused"; } @@ -824,8 +828,20 @@ code = 488; } - switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_NOTICE, "Rejecting with %d %s\n", code, reason); - nua_respond(tech_pvt->nh, code, reason, TAG_END()); + if (code == 407) { + const char *to_uri = switch_channel_get_variable(channel, "sip_to_uri"); + const char *to_host = reason; + + if (switch_strlen_zero(to_host)) { + to_host = switch_channel_get_variable(channel, "sip_to_host"); + } + switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_NOTICE, "Challanging call %s\n", to_uri); + sofia_reg_auth_challange(NULL, tech_pvt->profile, tech_pvt->nh, REG_INVITE, to_host, 0); + switch_channel_hangup(channel, SWITCH_CAUSE_USER_CHALLENGE); + } else { + switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_NOTICE, "Rejecting with %d %s\n", code, reason); + nua_respond(tech_pvt->nh, code, reason, TAG_END()); + } } } break; Modified: freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/mod_sofia.h ============================================================================== --- freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/mod_sofia.h (original) +++ freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/mod_sofia.h Tue Jun 12 15:20:17 2007 @@ -111,7 +111,8 @@ PFLAG_DISABLE_TRANSCODING = (1 << 6), PFLAG_REWRITE_TIMESTAMPS = (1 << 7), PFLAG_RUNNING = (1 << 8), - PFLAG_RESPAWN = (1 << 9) + PFLAG_RESPAWN = (1 << 9), + PFLAG_GREEDY = (1 << 10) } PFLAGS; @@ -428,6 +429,7 @@ void sofia_presence_mwi_event_handler(switch_event_t *event); void sofia_presence_cancel(void); switch_status_t config_sofia(int reload, char *profile_name); +void sofia_reg_auth_challange(nua_t *nua, sofia_profile_t *profile, nua_handle_t *nh, sofia_regtype_t regtype, const char *realm, int stale); auth_res_t sofia_reg_parse_auth(sofia_profile_t *profile, sip_authorization_t const *authorization, const char *regstr, char *np, size_t nplen, char *ip, switch_event_t **v_event); void sofia_reg_handle_sip_r_challenge(int status, Modified: freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia.c ============================================================================== --- freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia.c (original) +++ freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia.c Tue Jun 12 15:20:17 2007 @@ -797,6 +797,10 @@ if (switch_true(val)) { profile->pflags |= PFLAG_PASS_RFC2833; } + } else if (!strcasecmp(var, "inbound-codec-negotiation")) { + if (!strcasecmp(val, "greedy")) { + profile->pflags |= PFLAG_GREEDY; + } } else if (!strcasecmp(var, "disable-transcoding")) { if (switch_true(val)) { profile->pflags |= PFLAG_DISABLE_TRANSCODING; @@ -1737,6 +1741,7 @@ switch_event_t *v_event = NULL; uint32_t sess_count = switch_core_session_count(); uint32_t sess_max = switch_core_session_limit(0); + int is_auth = 0; if ((profile->soft_max && sess_count >= profile->soft_max) || sess_count >= sess_max) { nua_respond(nh, 480, "Maximum Calls In Progress", SIPTAG_RETRY_AFTER_STR("300"), TAG_END()); @@ -1755,14 +1760,15 @@ nua_respond(nh, 400, "Missing Contact Header", TAG_END()); return; } - - if ((profile->pflags & PFLAG_AUTH_CALLS)) { + + if ((profile->pflags & PFLAG_AUTH_CALLS) || sip->sip_proxy_authorization || sip->sip_authorization) { if (sofia_reg_handle_register(nua, profile, nh, sip, REG_INVITE, key, sizeof(key), &v_event)) { if (v_event) { switch_event_destroy(&v_event); } return; } + is_auth++; } if (!(session = switch_core_session_request(&sofia_endpoint_interface, NULL))) { @@ -1786,6 +1792,10 @@ get_addr(network_ip, sizeof(network_ip), &((struct sockaddr_in *) msg_addrinfo(nua_current_request(nua))->ai_addr)->sin_addr); channel = switch_core_session_get_channel(session); + if (is_auth) { + switch_channel_set_variable(channel, "sip_authorized", "true"); + } + if (v_event) { switch_event_header_t *hp; Modified: freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia_glue.c ============================================================================== --- freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia_glue.c (original) +++ freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia_glue.c Tue Jun 12 15:20:17 2007 @@ -41,7 +41,7 @@ { char buf[2048]; int ptime = 0; - int rate = 0; + uint32_t rate = 0; uint32_t v_port; if (!force && !ip && !sr && switch_channel_test_flag(tech_pvt->channel, CF_BYPASS_MEDIA)) { @@ -112,7 +112,7 @@ if (tech_pvt->rm_encoding) { rate = tech_pvt->rm_rate; - snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), "a=rtpmap:%d %s/%ld\n", tech_pvt->pt, tech_pvt->rm_encoding, tech_pvt->rm_rate); + snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), "a=rtpmap:%d %s/%d\n", tech_pvt->pt, tech_pvt->rm_encoding, rate); if (tech_pvt->fmtp_out) { snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), "a=fmtp:%d %s\n", tech_pvt->pt, tech_pvt->fmtp_out); } @@ -124,24 +124,18 @@ int i; for (i = 0; i < tech_pvt->num_codecs; i++) { const switch_codec_implementation_t *imp = tech_pvt->codecs[i]; - uint32_t rfc_3551_sucks = imp->samples_per_second; if (imp->codec_type != SWITCH_CODEC_TYPE_AUDIO) { continue; } - if (!rate) { - rate = imp->samples_per_second; - } + rate = imp->samples_per_second; + if (ptime && ptime != imp->microseconds_per_frame / 1000) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "ptime %u != advertised ptime %u\n", imp->microseconds_per_frame / 1000, ptime); } - if (rfc_3551_sucks && imp->ianacode == 9) { - rfc_3551_sucks = 8000; - } - - snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), "a=rtpmap:%d %s/%d\n", imp->ianacode, imp->iananame, rfc_3551_sucks); + snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), "a=rtpmap:%d %s/%d\n", imp->ianacode, imp->iananame, rate); if (imp->fmtp) { snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), "a=fmtp:%d %s\n", imp->ianacode, imp->fmtp); } @@ -152,7 +146,7 @@ snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), "a=rtpmap:%d telephone-event/8000\na=fmtp:%d 0-16\n", tech_pvt->te, tech_pvt->te); } if (tech_pvt->cng_pt) { - snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), "a=rtpmap:%d CN/%d\n", tech_pvt->cng_pt, rate); + snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), "a=rtpmap:%d CN/8000\n", tech_pvt->cng_pt); if (!tech_pvt->rm_encoding) { tech_pvt->cng_pt = 0; } @@ -814,8 +808,10 @@ int ms; tech_pvt->read_frame.rate = tech_pvt->rm_rate; ms = tech_pvt->write_codec.implementation->microseconds_per_frame / 1000; - switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Set Codec %s %s/%ld %d ms\n", - switch_channel_get_name(tech_pvt->channel), tech_pvt->rm_encoding, tech_pvt->rm_rate, tech_pvt->codec_ms); + switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Set Codec %s %s/%ld %d ms %d samples\n", + switch_channel_get_name(tech_pvt->channel), tech_pvt->rm_encoding, tech_pvt->rm_rate, tech_pvt->codec_ms, + tech_pvt->read_codec.implementation->samples_per_frame + ); tech_pvt->read_frame.codec = &tech_pvt->read_codec; switch_core_session_set_read_codec(tech_pvt->session, &tech_pvt->read_codec); @@ -1042,12 +1038,25 @@ private_object_t *tech_pvt; sdp_media_t *m; sdp_attribute_t *a; - + int first = 0, last = 0; int ptime = 0, dptime = 0; + int greedy = 0, x = 0, skip = 0, mine = 0; + switch_channel_t *channel = NULL; + char *val; tech_pvt = switch_core_session_get_private(session); assert(tech_pvt != NULL); + channel = switch_core_session_get_channel(session); + assert(channel != NULL); + + greedy = !!(tech_pvt->profile->pflags & PFLAG_GREEDY); + + if (!greedy) { + if ((val = switch_channel_get_variable(channel, "sip_codec_negotiation")) && !strcasecmp(val, "greedy")) { + greedy = 1; + } + } if ((tech_pvt->origin = switch_core_session_strdup(session, (char *) sdp->sdp_origin->o_username))) { if (strstr(tech_pvt->origin, "CiscoSystemsSIP-GW-UserAgent")) { @@ -1108,12 +1117,18 @@ match = 0; break; } - + + greed: + x = 0; for (map = m->m_rtpmaps; map; map = map->rm_next) { int32_t i; const switch_codec_implementation_t *mimp = NULL, *near_match = NULL; const char *rm_encoding; - + + if (x++ < skip) { + printf("skip %s\n", map->rm_encoding); + continue; + } if (!(rm_encoding = map->rm_encoding)) { rm_encoding = ""; @@ -1135,25 +1150,28 @@ switch_rtp_set_flag(tech_pvt->rtp_session, SWITCH_RTP_FLAG_AUTO_CNG); } } - + if (match) { if (te && cng_pt) { break; } continue; } + + if (greedy) { + first = mine; + last = first + 1; + } else { + first = 0; last = tech_pvt->num_codecs; + } - for (i = 0; i < tech_pvt->num_codecs; i++) { + for (i = first; i < last && i < tech_pvt->num_codecs; i++) { const switch_codec_implementation_t *imp = tech_pvt->codecs[i]; uint32_t codec_rate = imp->samples_per_second; if (imp->codec_type != SWITCH_CODEC_TYPE_AUDIO) { continue; } - if (map->rm_pt == 9) { - switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Oh sure! You say 8000, but you mean 16000! This is, of course, stupid!\n"); - codec_rate = 8000; - } switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Audio Codec Compare [%s:%d:%u]/[%s:%d:%u]\n", rm_encoding, map->rm_pt, (int)map->rm_rate, imp->iananame, imp->ianacode, codec_rate); if (map->rm_pt < 96) { @@ -1174,6 +1192,11 @@ match = 0; } } + + if (!match && greedy) { + skip++; + continue; + } if (!match && near_match) { const switch_codec_implementation_t *search[1]; @@ -1182,7 +1205,7 @@ int num; snprintf(tmp, sizeof(tmp), "%s@%uk@%ui", near_match->iananame, near_match->samples_per_second, ptime); - + prefs[0] = tmp; num = switch_loadable_module_get_codecs_sorted(search, 1, prefs, 1); @@ -1221,6 +1244,13 @@ } } } + + if (!match && greedy && mine < tech_pvt->num_codecs) { + mine++; + skip = 0; + goto greed; + } + } else if (m->m_type == sdp_media_video) { sdp_rtpmap_t *map; const char *rm_encoding; Modified: freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia_reg.c ============================================================================== --- freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia_reg.c (original) +++ freeswitch/branches/greenlizard/src/mod/endpoints/mod_sofia/sofia_reg.c Tue Jun 12 15:20:17 2007 @@ -272,6 +272,36 @@ } } + +void sofia_reg_auth_challange(nua_t *nua, sofia_profile_t *profile, nua_handle_t *nh, sofia_regtype_t regtype, const char *realm, int stale) +{ + switch_uuid_t uuid; + char uuid_str[SWITCH_UUID_FORMATTED_LENGTH + 1]; + char *sql, *auth_str; + + switch_uuid_get(&uuid); + switch_uuid_format(uuid_str, &uuid); + + switch_mutex_lock(profile->ireg_mutex); + sql = switch_mprintf("insert into sip_authentication (nonce, expires) values('%q', %ld)", + uuid_str, time(NULL) + profile->nonce_ttl); + assert(sql != NULL); + sofia_glue_execute_sql(profile, SWITCH_FALSE, sql, NULL); + switch_safe_free(sql); + switch_mutex_unlock(profile->ireg_mutex); + + auth_str = + switch_mprintf("Digest realm=\"%q\", nonce=\"%q\",%s algorithm=MD5, qop=\"auth\"", realm, uuid_str, stale ? " stale=\"true\"," : ""); + + if (regtype == REG_REGISTER) { + nua_respond(nh, SIP_401_UNAUTHORIZED, TAG_IF(nua, NUTAG_WITH_THIS(nua)), SIPTAG_WWW_AUTHENTICATE_STR(auth_str), TAG_END()); + } else if (regtype == REG_INVITE) { + nua_respond(nh, SIP_407_PROXY_AUTH_REQUIRED, TAG_IF(nua, NUTAG_WITH_THIS(nua)), SIPTAG_PROXY_AUTHENTICATE_STR(auth_str), TAG_END()); + } + + switch_safe_free(auth_str); +} + uint8_t sofia_reg_handle_register(nua_t * nua, sofia_profile_t *profile, nua_handle_t * nh, sip_t const *sip, sofia_regtype_t regtype, char *key, uint32_t keylen, switch_event_t **v_event) { @@ -396,32 +426,11 @@ } if (!authorization || stale) { - switch_uuid_t uuid; - char uuid_str[SWITCH_UUID_FORMATTED_LENGTH + 1]; - char *sql, *auth_str; - - switch_uuid_get(&uuid); - switch_uuid_format(uuid_str, &uuid); - - switch_mutex_lock(profile->ireg_mutex); - sql = switch_mprintf("insert into sip_authentication (nonce, expires) values('%q', %ld)", - uuid_str, time(NULL) + profile->nonce_ttl); - assert(sql != NULL); - sofia_glue_execute_sql(profile, SWITCH_FALSE, sql, NULL); - switch_safe_free(sql); - switch_mutex_unlock(profile->ireg_mutex); - - auth_str = - switch_mprintf("Digest realm=\"%q\", nonce=\"%q\",%s algorithm=MD5, qop=\"auth\"", to_host, uuid_str, stale ? " stale=\"true\"," : ""); + sofia_reg_auth_challange(nua, profile, nh, regtype, to_host, stale); if (regtype == REG_REGISTER) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Requesting Registration from: [%s@%s]\n", to_user, to_host); - nua_respond(nh, SIP_401_UNAUTHORIZED, NUTAG_WITH_THIS(nua), SIPTAG_WWW_AUTHENTICATE_STR(auth_str), TAG_END()); - } else if (regtype == REG_INVITE) { - nua_respond(nh, SIP_407_PROXY_AUTH_REQUIRED, NUTAG_WITH_THIS(nua), SIPTAG_PROXY_AUTHENTICATE_STR(auth_str), TAG_END()); } - - switch_safe_free(auth_str); return 1; } reg: Modified: freeswitch/branches/greenlizard/src/mod/formats/mod_shout/mod_shout.c ============================================================================== --- freeswitch/branches/greenlizard/src/mod/formats/mod_shout/mod_shout.c (original) +++ freeswitch/branches/greenlizard/src/mod/formats/mod_shout/mod_shout.c Tue Jun 12 15:20:17 2007 @@ -65,6 +65,7 @@ int samplerate; uint8_t thread_running; uint8_t shout_init; + uint32_t prebuf; }; typedef struct shout_context shout_context_t; @@ -335,6 +336,10 @@ error_check(); + if (context->prebuf) { + buf_size = context->prebuf; + } + /* make sure we aren't over zealous by slowing down the stream when the buffer is too full */ for (;;) { error_check(); @@ -349,10 +354,11 @@ switch_mutex_unlock(context->audio_mutex); if (used < buf_size) { + //switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Buffered %u/%u!\n", used, buf_size); break; } - switch_yield(1000000); + switch_yield(500000); } error_check(); @@ -555,6 +561,7 @@ InitMP3(&context->mp, OUTSCALE, context->samplerate); if (handle->handler) { context->stream_url = switch_core_sprintf(context->memory_pool, "http://%s", path); + context->prebuf = handle->prebuf; launch_read_stream_thread(context); } else { if (switch_file_open(&context->fd, path, SWITCH_FOPEN_READ, SWITCH_FPROT_UREAD | SWITCH_FPROT_UWRITE, handle->memory_pool) != Modified: freeswitch/branches/greenlizard/src/mod/languages/mod_spidermonkey/mod_spidermonkey.c ============================================================================== --- freeswitch/branches/greenlizard/src/mod/languages/mod_spidermonkey/mod_spidermonkey.c (original) +++ freeswitch/branches/greenlizard/src/mod/languages/mod_spidermonkey/mod_spidermonkey.c Tue Jun 12 15:20:17 2007 @@ -1357,6 +1357,7 @@ switch_file_handle_t fh = { 0 }; JSFunction *function; switch_input_args_t args = { 0 }; + char *prebuf; if (!jss || !jss->session) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "You must call the session.originate method before calling this method!\n"); @@ -1404,6 +1405,14 @@ JS_ValueToInt32(cx, argv[3], &samps); fh.samples = samps; } + + if ((prebuf = switch_channel_get_variable(channel, "stream_prebuffer"))) { + int maybe = atoi(prebuf); + if (maybe > 0) { + fh.prebuf = maybe; + } + } + cb_state.extra = &fh; cb_state.ret = BOOLEAN_TO_JSVAL(JS_FALSE); Modified: freeswitch/branches/greenlizard/src/switch_channel.c ============================================================================== --- freeswitch/branches/greenlizard/src/switch_channel.c (original) +++ freeswitch/branches/greenlizard/src/switch_channel.c Tue Jun 12 15:20:17 2007 @@ -96,6 +96,7 @@ {"BLIND_TRANSFER", SWITCH_CAUSE_BLIND_TRANSFER}, {"ATTENDED_TRANSFER", SWITCH_CAUSE_ATTENDED_TRANSFER}, {"ALLOTTED_TIMEOUT", SWITCH_CAUSE_ALLOTTED_TIMEOUT}, + {"USER_CHALLENGE", SWITCH_CAUSE_USER_CHALLENGE}, {NULL, 0} }; Modified: freeswitch/branches/greenlizard/src/switch_core.c ============================================================================== --- freeswitch/branches/greenlizard/src/switch_core.c (original) +++ freeswitch/branches/greenlizard/src/switch_core.c Tue Jun 12 15:20:17 2007 @@ -58,7 +58,7 @@ "%u minute%s, " "%u second%s, " "%u millisecond%s, " - "%u microsecond%s\n", + "%u microsecond%s", duration.yr, duration.yr == 1 ? "" : "s", duration.day, duration.day == 1 ? "" : "s", duration.hr, duration.hr == 1 ? "" : "s", Modified: freeswitch/branches/greenlizard/src/switch_cpp.cpp ============================================================================== --- freeswitch/branches/greenlizard/src/switch_cpp.cpp (original) +++ freeswitch/branches/greenlizard/src/switch_cpp.cpp Tue Jun 12 15:20:17 2007 @@ -204,6 +204,7 @@ switch_file_handle_t fh = { 0 }; unsigned int samps; unsigned int pos = 0; + char *prebuf; sanity_check(-1); fh.samples = starting_sample_count; @@ -213,6 +214,13 @@ status = switch_ivr_play_file(session, &fh, file, ap); end_allow_threads(); + if ((prebuf = switch_channel_get_variable(this->channel, "stream_prebuffer"))) { + int maybe = atoi(prebuf); + if (maybe > 0) { + fh.prebuf = maybe; + } + } + return status == SWITCH_STATUS_SUCCESS ? 1 : 0; } Modified: freeswitch/branches/greenlizard/src/switch_ivr_play_say.c ============================================================================== --- freeswitch/branches/greenlizard/src/switch_ivr_play_say.c (original) +++ freeswitch/branches/greenlizard/src/switch_ivr_play_say.c Tue Jun 12 15:20:17 2007 @@ -505,6 +505,7 @@ char *ext; char *prefix; char *timer_name; + char *prebuf; channel = switch_core_session_get_channel(session); assert(channel != NULL); @@ -512,6 +513,7 @@ prefix = switch_channel_get_variable(channel, "sound_prefix"); timer_name = switch_channel_get_variable(channel, "timer_name"); + if (!file) { return SWITCH_STATUS_FALSE; } @@ -552,6 +554,15 @@ fh->samples = 0; } + if ((prebuf = switch_channel_get_variable(channel, "stream_prebuffer"))) { + int maybe = atoi(prebuf); + if (maybe > 0) { + fh->prebuf = maybe; + } + } + + + if (switch_core_file_open(fh, file, read_codec->implementation->number_of_channels, Modified: freeswitch/branches/greenlizard/src/switch_rtp.c ============================================================================== --- freeswitch/branches/greenlizard/src/switch_rtp.c (original) +++ freeswitch/branches/greenlizard/src/switch_rtp.c Tue Jun 12 15:20:17 2007 @@ -1281,9 +1281,12 @@ send_msg = (rtp_msg_t *) data; } else { uint8_t m = 0; - if (rtp_session->ts > rtp_session->last_write_ts + rtp_session->samples_per_interval || rtp_session->ts == rtp_session->samples_per_interval) { + + if ((rtp_session->ts > (rtp_session->last_write_ts + (rtp_session->samples_per_interval * 10))) + || rtp_session->ts == rtp_session->samples_per_interval) { m++; } + if (rtp_session->cn && payload != rtp_session->cng_pt) { rtp_session->cn = 0; m++; @@ -1365,7 +1368,7 @@ } send = 1; } else { - if (score > rtp_session->vad_data.bg_level) { + if (score > rtp_session->vad_data.bg_level && !switch_test_flag(&rtp_session->vad_data, SWITCH_VAD_FLAG_TALKING)) { uint32_t diff = score - rtp_session->vad_data.bg_level; if (rtp_session->vad_data.hangover_hits) { @@ -1373,6 +1376,7 @@ } if (diff >= rtp_session->vad_data.diff_level || ++rtp_session->vad_data.hangunder_hits >= rtp_session->vad_data.hangunder) { + switch_set_flag(&rtp_session->vad_data, SWITCH_VAD_FLAG_TALKING); send_msg->header.m = 1; rtp_session->vad_data.hangover_hits = rtp_session->vad_data.hangunder_hits = rtp_session->vad_data.cng_count = 0;