diff --git a/coreapi/linphonecall.c b/coreapi/linphonecall.c index 6ec9acc9f..ff2f4c4ba 100644 --- a/coreapi/linphonecall.c +++ b/coreapi/linphonecall.c @@ -3136,6 +3136,7 @@ static void linphone_call_start_audio_stream(LinphoneCall *call, LinphoneCallSta if (used_pt!=-1){ bool_t ok = TRUE; call->current_params->audio_codec = rtp_profile_get_payload(call->audio_profile, used_pt); + call->current_params->has_audio = TRUE; if (playcard==NULL) { ms_warning("No card defined for playback !"); } @@ -3596,6 +3597,7 @@ void linphone_call_start_media_streams(LinphoneCall *call, LinphoneCallState nex ms_message("linphone_call_start_media_streams() call=[%p] local upload_bandwidth=[%i] kbit/s; local download_bandwidth=[%i] kbit/s", call, linphone_core_get_upload_bandwidth(lc),linphone_core_get_download_bandwidth(lc)); + call->current_params->has_audio = FALSE; if (call->audiostream!=NULL) { linphone_call_start_audio_stream(call, next_state, use_arc); } else { diff --git a/coreapi/misc.c b/coreapi/misc.c index 6eaacc70d..5a2eff5bf 100644 --- a/coreapi/misc.c +++ b/coreapi/misc.c @@ -703,7 +703,7 @@ int linphone_core_gather_ice_candidates(LinphoneCore *lc, LinphoneCall *call){ audio_cl = ice_session_check_list(call->ice_session, call->main_audio_stream_index); video_cl = ice_session_check_list(call->ice_session, call->main_video_stream_index); text_cl = ice_session_check_list(call->ice_session, call->main_text_stream_index); - if (audio_cl == NULL) return -1; + if ((audio_cl == NULL) && (video_cl == NULL) && (text_cl == NULL)) return -1; if ((nat_policy != NULL) && (server != NULL) && (server[0] != '\0')) { ai=linphone_nat_policy_get_stun_server_addrinfo(nat_policy); @@ -784,7 +784,7 @@ void linphone_core_update_ice_state_in_call_stats(LinphoneCall *call) audio_check_list = ice_session_check_list(call->ice_session, call->main_audio_stream_index); video_check_list = ice_session_check_list(call->ice_session, call->main_video_stream_index); text_check_list = ice_session_check_list(call->ice_session, call->main_text_stream_index); - if (audio_check_list == NULL) return; + if ((audio_check_list == NULL) && (video_check_list == NULL) && (text_check_list == NULL)) return; session_state = ice_session_state(call->ice_session); if ((session_state == IS_Completed) || ((session_state == IS_Failed) && (ice_session_has_completed_check_list(call->ice_session) == TRUE))) { @@ -902,10 +902,20 @@ void _update_local_media_description_from_ice(SalMediaDescription *desc, IceSess int nb_candidates; int i; int j; - bool_t result; + bool_t result = FALSE; if (session_state == IS_Completed) { - result = ice_check_list_selected_valid_local_candidate(ice_session_check_list(session, 0), &rtp_candidate, NULL); + IceCheckList *first_cl = NULL; + for (i = 0; i < desc->nb_streams; i++) { + IceCheckList *cl = ice_session_check_list(session, i); + if (cl != NULL) { + first_cl = cl; + break; + } + } + if (first_cl != NULL) { + result = ice_check_list_selected_valid_local_candidate(first_cl, &rtp_candidate, NULL); + } if (result == TRUE) { strncpy(desc->addr, rtp_candidate->taddr.ip, sizeof(desc->addr)); } else { diff --git a/tester/call_video_tester.c b/tester/call_video_tester.c index 8c61f7396..bc8f72d50 100644 --- a/tester/call_video_tester.c +++ b/tester/call_video_tester.c @@ -908,7 +908,7 @@ static void call_with_ice_video_to_novideo(void) { * It doesn't use linphone_core_accept_call_with_params() to accept video despite of default policies. */ static void _call_with_ice_video(LinphoneVideoPolicy caller_policy, LinphoneVideoPolicy callee_policy, - bool_t video_added_by_caller, bool_t video_added_by_callee, bool_t video_removed_by_caller, bool_t video_removed_by_callee) { + bool_t video_added_by_caller, bool_t video_added_by_callee, bool_t video_removed_by_caller, bool_t video_removed_by_callee, bool_t video_only) { LinphoneCoreManager *marie = linphone_core_manager_new("marie_rc"); LinphoneCoreManager* pauline = linphone_core_manager_new(transport_supported(LinphoneTransportTls) ? "pauline_rc" : "pauline_tcp_rc"); unsigned int nb_media_starts = 1; @@ -928,7 +928,11 @@ static void _call_with_ice_video(LinphoneVideoPolicy caller_policy, LinphoneVide linphone_core_set_video_policy(marie->lc, &callee_policy); linphone_core_set_firewall_policy(marie->lc, LinphonePolicyUseIce); linphone_core_set_firewall_policy(pauline->lc, LinphonePolicyUseIce); - + if (video_only) { + linphone_core_enable_payload_type(marie->lc, linphone_core_find_payload_type(marie->lc, "PCMU", 8000, 1), FALSE); /* Disable PCMU */ + linphone_core_enable_payload_type(marie->lc, linphone_core_find_payload_type(marie->lc, "PCMA", 8000, 1), TRUE); /* Enable PCMA */ + } + linphone_core_manager_wait_for_stun_resolution(marie); linphone_core_manager_wait_for_stun_resolution(pauline); @@ -1015,7 +1019,7 @@ static void call_with_ice_video_added(void) { * Scenario: video is not active at the beginning of the call, caller requests it but callee declines it */ LinphoneVideoPolicy vpol = { FALSE, FALSE }; - _call_with_ice_video(vpol, vpol, TRUE, FALSE, FALSE, FALSE); + _call_with_ice_video(vpol, vpol, TRUE, FALSE, FALSE, FALSE, FALSE); } static void call_with_ice_video_added_2(void) { @@ -1023,7 +1027,7 @@ static void call_with_ice_video_added_2(void) { /* * Scenario: video is not active at the beginning of the call, callee requests it but caller declines it */ - _call_with_ice_video(vpol, vpol, FALSE, TRUE, FALSE, FALSE); + _call_with_ice_video(vpol, vpol, FALSE, TRUE, FALSE, FALSE, FALSE); } static void call_with_ice_video_added_3(void) { @@ -1033,7 +1037,7 @@ static void call_with_ice_video_added_3(void) { * Scenario: video is not active at the beginning of the call, caller requests it and callee accepts. * Finally caller removes it. */ - _call_with_ice_video(caller_policy, callee_policy, TRUE, FALSE, TRUE, FALSE); + _call_with_ice_video(caller_policy, callee_policy, TRUE, FALSE, TRUE, FALSE, FALSE); } static void call_with_ice_video_added_4(void) { @@ -1043,7 +1047,7 @@ static void call_with_ice_video_added_4(void) { * Scenario: video is not active at the beginning of the call, callee requests it and caller accepts. * Finally caller removes it. */ - _call_with_ice_video(caller_policy, callee_policy, FALSE, TRUE, TRUE, FALSE); + _call_with_ice_video(caller_policy, callee_policy, FALSE, TRUE, TRUE, FALSE, FALSE); } static void call_with_ice_video_added_5(void) { @@ -1053,7 +1057,7 @@ static void call_with_ice_video_added_5(void) { * Scenario: video is not active at the beginning of the call, callee requests it and caller accepts. * Finally callee removes it. */ - _call_with_ice_video(caller_policy, callee_policy, FALSE, TRUE, FALSE, TRUE); + _call_with_ice_video(caller_policy, callee_policy, FALSE, TRUE, FALSE, TRUE, FALSE); } static void call_with_ice_video_added_6(void) { @@ -1062,7 +1066,7 @@ static void call_with_ice_video_added_6(void) { /* * Scenario: video is active at the beginning of the call, caller removes it. */ - _call_with_ice_video(caller_policy, callee_policy, FALSE, FALSE, TRUE, FALSE); + _call_with_ice_video(caller_policy, callee_policy, FALSE, FALSE, TRUE, FALSE, FALSE); } static void call_with_ice_video_added_7(void) { @@ -1071,7 +1075,7 @@ static void call_with_ice_video_added_7(void) { /* * Scenario: video is active at the beginning of the call, callee removes it. */ - _call_with_ice_video(caller_policy, callee_policy, FALSE, FALSE, FALSE, TRUE); + _call_with_ice_video(caller_policy, callee_policy, FALSE, FALSE, FALSE, TRUE, FALSE); } static void call_with_ice_video_and_rtt(void) { @@ -1120,6 +1124,14 @@ end: linphone_core_manager_destroy(pauline); } +static void call_with_ice_video_only(void) { + LinphoneVideoPolicy caller_policy = { TRUE, TRUE }; + LinphoneVideoPolicy callee_policy = { TRUE, TRUE }; + /* + * Scenario: video is active at the beginning of the call, but no audio codecs match. + */ + _call_with_ice_video(caller_policy, callee_policy, FALSE, FALSE, FALSE, FALSE, TRUE); +} static void video_call_with_early_media_no_matching_audio_codecs(void) { LinphoneCoreManager *marie = linphone_core_manager_new("marie_rc"); @@ -1875,6 +1887,7 @@ test_t call_video_tests[] = { TEST_ONE_TAG("Call with ICE and video added 6", call_with_ice_video_added_6, "ICE"), TEST_ONE_TAG("Call with ICE and video added 7", call_with_ice_video_added_7, "ICE"), TEST_ONE_TAG("Call with ICE, video and realtime text", call_with_ice_video_and_rtt, "ICE"), + TEST_ONE_TAG("Call with ICE, video only", call_with_ice_video_only, "ICE"), TEST_ONE_TAG("Video call with ICE accepted using call params", video_call_ice_params, "ICE"), TEST_ONE_TAG("Audio call with ICE paused with caller video policy enabled", audio_call_with_ice_with_video_policy_enabled, "ICE"), TEST_NO_TAG("Video call recording (H264)", video_call_recording_h264_test), diff --git a/tester/tester.c b/tester/tester.c index f5d676031..c2be6ce4b 100644 --- a/tester/tester.c +++ b/tester/tester.c @@ -718,10 +718,11 @@ static void check_ice_from_rtp(LinphoneCall *c1, LinphoneCall *c2, LinphoneStrea bool_t check_ice(LinphoneCoreManager* caller, LinphoneCoreManager* callee, LinphoneIceState state) { LinphoneCall *c1,*c2; + bool_t global_success = TRUE; bool_t audio_success=FALSE; bool_t video_success=FALSE; bool_t text_success=FALSE; - bool_t video_enabled, realtime_text_enabled; + bool_t audio_enabled, video_enabled, realtime_text_enabled; MSTimeSpec ts; c1=linphone_core_get_current_call(caller->lc); @@ -735,23 +736,26 @@ bool_t check_ice(LinphoneCoreManager* caller, LinphoneCoreManager* callee, Linph BC_ASSERT_EQUAL(linphone_call_params_video_enabled(linphone_call_get_current_params(c1)),linphone_call_params_video_enabled(linphone_call_get_current_params(c2)), int, "%d"); BC_ASSERT_EQUAL(linphone_call_params_realtime_text_enabled(linphone_call_get_current_params(c1)),linphone_call_params_realtime_text_enabled(linphone_call_get_current_params(c2)), int, "%d"); + audio_enabled=linphone_call_params_audio_enabled(linphone_call_get_current_params(c1)); video_enabled=linphone_call_params_video_enabled(linphone_call_get_current_params(c1)); realtime_text_enabled=linphone_call_params_realtime_text_enabled(linphone_call_get_current_params(c1)); - liblinphone_tester_clock_start(&ts); - do{ - if ((c1 != NULL) && (c2 != NULL)) { - if (linphone_call_get_audio_stats(c1)->ice_state==state && - linphone_call_get_audio_stats(c2)->ice_state==state ){ - audio_success=TRUE; - check_ice_from_rtp(c1,c2,LinphoneStreamTypeAudio); - check_ice_from_rtp(c2,c1,LinphoneStreamTypeAudio); - break; + if (audio_enabled) { + liblinphone_tester_clock_start(&ts); + do{ + if ((c1 != NULL) && (c2 != NULL)) { + if (linphone_call_get_audio_stats(c1)->ice_state==state && + linphone_call_get_audio_stats(c2)->ice_state==state ){ + audio_success=TRUE; + check_ice_from_rtp(c1,c2,LinphoneStreamTypeAudio); + check_ice_from_rtp(c2,c1,LinphoneStreamTypeAudio); + break; + } + linphone_core_iterate(caller->lc); + linphone_core_iterate(callee->lc); } - linphone_core_iterate(caller->lc); - linphone_core_iterate(callee->lc); - } - ms_usleep(20000); - }while(!liblinphone_tester_clock_elapsed(&ts,10000)); + ms_usleep(20000); + }while(!liblinphone_tester_clock_elapsed(&ts,10000)); + } if (video_enabled){ liblinphone_tester_clock_start(&ts); @@ -800,7 +804,10 @@ bool_t check_ice(LinphoneCoreManager* caller, LinphoneCoreManager* callee, Linph } linphone_call_unref(c1); linphone_call_unref(c2); - return video_enabled ? (realtime_text_enabled ? text_success && audio_success && video_success : audio_success && video_success) : realtime_text_enabled ? text_success && audio_success : audio_success; + if (audio_enabled) global_success = global_success && audio_success; + if (video_enabled) global_success = global_success && video_success; + if (realtime_text_enabled) global_success = global_success && text_success; + return global_success; } static void linphone_conference_server_call_state_changed(LinphoneCore *lc, LinphoneCall *call, LinphoneCallState cstate, const char *msg) {