From 274d50168e63f8071250d8abf4f6a32fac86ef6e Mon Sep 17 00:00:00 2001 From: Simon Morlat Date: Wed, 2 Apr 2014 22:23:04 +0200 Subject: [PATCH] implement digest authentication for anonymous calls (with id privacy) --- coreapi/bellesip_sal/sal_impl.c | 8 +++- coreapi/bellesip_sal/sal_op_impl.c | 9 ++++- tester/call_tester.c | 60 ++++++++++++++++++++++++++++++ tester/flexisip.conf | 2 +- 4 files changed, 75 insertions(+), 4 deletions(-) diff --git a/coreapi/bellesip_sal/sal_impl.c b/coreapi/bellesip_sal/sal_impl.c index c0340e56a..e4d72e834 100644 --- a/coreapi/bellesip_sal/sal_impl.c +++ b/coreapi/bellesip_sal/sal_impl.c @@ -115,7 +115,13 @@ void sal_process_authentication(SalOp *op) { belle_sip_list_t* auth_list=NULL; belle_sip_auth_event_t* auth_event; belle_sip_response_t *response=belle_sip_transaction_get_response((belle_sip_transaction_t*)op->pending_auth_transaction); + belle_sip_header_from_t *from=belle_sip_message_get_header_by_type(initial_request,belle_sip_header_from_t); + belle_sip_uri_t *from_uri=belle_sip_header_address_get_uri((belle_sip_header_address_t*)from); + if (strcasecmp(belle_sip_uri_get_host(from_uri),"anonymous.invalid")==0){ + /*prefer using the from from the SalOp*/ + from_uri=belle_sip_header_address_get_uri((belle_sip_header_address_t*)sal_op_get_from_address(op)); + } if (op->dialog && belle_sip_dialog_get_state(op->dialog)==BELLE_SIP_DIALOG_CONFIRMED) { new_request = belle_sip_dialog_create_request_from(op->dialog,initial_request); @@ -132,7 +138,7 @@ void sal_process_authentication(SalOp *op) { return; } - if (belle_sip_provider_add_authorization(op->base.root->prov,new_request,response,&auth_list)) { + if (belle_sip_provider_add_authorization(op->base.root->prov,new_request,response,from_uri,&auth_list)) { if (is_within_dialog) { sal_op_send_request(op,new_request); } else { diff --git a/coreapi/bellesip_sal/sal_op_impl.c b/coreapi/bellesip_sal/sal_op_impl.c index 3e5ebe2a5..a6020791e 100644 --- a/coreapi/bellesip_sal/sal_op_impl.c +++ b/coreapi/bellesip_sal/sal_op_impl.c @@ -90,18 +90,23 @@ SalAuthInfo * sal_op_get_auth_requested(SalOp *op){ belle_sip_header_contact_t* sal_op_create_contact(SalOp *op){ belle_sip_header_contact_t* contact_header; belle_sip_uri_t* contact_uri; + if (sal_op_get_contact_address(op)) { contact_header = belle_sip_header_contact_create(BELLE_SIP_HEADER_ADDRESS(sal_op_get_contact_address(op))); } else { contact_header= belle_sip_header_contact_new(); } + if (!(contact_uri=belle_sip_header_address_get_uri(BELLE_SIP_HEADER_ADDRESS(contact_header)))) { /*no uri, just creating a new one*/ contact_uri=belle_sip_uri_new(); belle_sip_header_address_set_uri(BELLE_SIP_HEADER_ADDRESS(contact_header),contact_uri); } + belle_sip_uri_set_secure(contact_uri,sal_op_is_secure(op)); - + if (op->privacy!=SalPrivacyNone){ + belle_sip_uri_set_user(contact_uri,NULL); + } belle_sip_header_contact_set_automatic(contact_header,op->base.root->auto_contacts); if (op->base.root->uuid){ if (belle_sip_parameters_has_parameter(BELLE_SIP_PARAMETERS(contact_header),"+sip.instance")==0){ @@ -299,7 +304,7 @@ static int _sal_op_send_request_with_contact(SalOp* op, belle_sip_request_t* req if (!belle_sip_message_get_header(BELLE_SIP_MESSAGE(request),BELLE_SIP_AUTHORIZATION) && !belle_sip_message_get_header(BELLE_SIP_MESSAGE(request),BELLE_SIP_PROXY_AUTHORIZATION)) { /*hmm just in case we already have authentication param in cache*/ - belle_sip_provider_add_authorization(op->base.root->prov,request,NULL,NULL); + belle_sip_provider_add_authorization(op->base.root->prov,request,NULL,NULL,NULL); } result = belle_sip_client_transaction_send_request_to(client_transaction,next_hop_uri/*might be null*/); diff --git a/tester/call_tester.c b/tester/call_tester.c index ed44faa9e..419def8cc 100644 --- a/tester/call_tester.c +++ b/tester/call_tester.c @@ -886,6 +886,65 @@ static void call_with_privacy(void) { linphone_core_manager_destroy(pauline); } +/*this ones makes call with privacy without previous registration*/ +static void call_with_privacy2(void) { + LinphoneCoreManager* marie = linphone_core_manager_new( "marie_rc"); + LinphoneCoreManager* pauline = linphone_core_manager_new2( "pauline_rc",FALSE); + LinphoneCall *c1,*c2; + LinphoneCallParams *params; + LinphoneProxyConfig* pauline_proxy; + params=linphone_core_create_default_call_parameters(pauline->lc); + linphone_call_params_set_privacy(params,LinphonePrivacyId); + + linphone_core_get_default_proxy(pauline->lc,&pauline_proxy); + linphone_proxy_config_edit(pauline_proxy); + linphone_proxy_config_enable_register(pauline_proxy,FALSE); + linphone_proxy_config_done(pauline_proxy); + + CU_ASSERT_TRUE(call_with_caller_params(pauline,marie,params)); + linphone_call_params_destroy(params); + + c1=linphone_core_get_current_call(pauline->lc); + c2=linphone_core_get_current_call(marie->lc); + + CU_ASSERT_PTR_NOT_NULL(c1); + CU_ASSERT_PTR_NOT_NULL(c2); + + /*make sure local identity is unchanged*/ + CU_ASSERT_TRUE(linphone_address_weak_equal(linphone_call_log_get_from(linphone_call_get_call_log(c1)),pauline->identity)); + + /*make sure remote identity is hidden*/ + CU_ASSERT_FALSE(linphone_address_weak_equal(linphone_call_get_remote_address(c2),pauline->identity)); + + CU_ASSERT_EQUAL(linphone_call_params_get_privacy(linphone_call_get_current_params(c2)),LinphonePrivacyId); + + /*just to sleep*/ + linphone_core_terminate_all_calls(pauline->lc); + CU_ASSERT_TRUE(wait_for(pauline->lc,marie->lc,&pauline->stat.number_of_LinphoneCallEnd,1)); + CU_ASSERT_TRUE(wait_for(pauline->lc,marie->lc,&marie->stat.number_of_LinphoneCallEnd,1)); + + /*test proxy config privacy*/ + linphone_proxy_config_set_privacy(pauline_proxy,LinphonePrivacyId); + + CU_ASSERT_TRUE(call(pauline,marie)); + c1=linphone_core_get_current_call(pauline->lc); + c2=linphone_core_get_current_call(marie->lc); + + CU_ASSERT_PTR_NOT_NULL(c1); + CU_ASSERT_PTR_NOT_NULL(c2); + + /*make sure remote identity is hidden*/ + CU_ASSERT_FALSE(linphone_address_weak_equal(linphone_call_get_remote_address(c2),pauline->identity)); + + CU_ASSERT_EQUAL(linphone_call_params_get_privacy(linphone_call_get_current_params(c2)),LinphonePrivacyId); + /*just to sleep*/ + linphone_core_terminate_all_calls(pauline->lc); + CU_ASSERT_TRUE(wait_for(pauline->lc,marie->lc,&pauline->stat.number_of_LinphoneCallEnd,2)); + CU_ASSERT_TRUE(wait_for(pauline->lc,marie->lc,&marie->stat.number_of_LinphoneCallEnd,2)); + + linphone_core_manager_destroy(marie); + linphone_core_manager_destroy(pauline); +} static void call_waiting_indication_with_param(bool_t enable_caller_privacy) { LinphoneCoreManager* marie = linphone_core_manager_new( "marie_rc"); @@ -1801,6 +1860,7 @@ test_t call_tests[] = { { "SRTP ice call", srtp_ice_call }, #endif { "Call with privacy", call_with_privacy }, + { "Call with privacy 2", call_with_privacy2 }, { "Call rejected because of wrong credential", call_rejected_because_wrong_credentials}, { "Call rejected without 403 because of wrong credential", call_rejected_without_403_because_wrong_credentials}, { "Call rejected without 403 because of wrong credential and no auth req cb", call_rejected_without_403_because_wrong_credentials_no_auth_req_cb}, diff --git a/tester/flexisip.conf b/tester/flexisip.conf index a5cac58fc..48f4a054b 100755 --- a/tester/flexisip.conf +++ b/tester/flexisip.conf @@ -128,7 +128,7 @@ no-403=user-agent contains 'tester-no-403' # in 'a.org b.org c.org', (to.uri.domain in 'a.org b.org c.org') # && (user-agent == 'Linphone v2') # Default value: -filter= from.uri.domain contains 'sip.example.org' || from.uri.domain contains 'auth.example.org' || from.uri.domain contains 'auth1.example.org' || from.uri.domain contains 'auth2.example.org' +filter= from.uri.domain contains 'sip.example.org' || from.uri.domain contains 'auth.example.org' || from.uri.domain contains 'auth1.example.org' || from.uri.domain contains 'auth2.example.org' || from.uri.domain contains 'anonymous.invalid' # List of whitespace separated domain names to challenge. Others # are denied.