diff --git a/coreapi/linphonecore.c b/coreapi/linphonecore.c index bb44d5da3..f78a5d5cd 100644 --- a/coreapi/linphonecore.c +++ b/coreapi/linphonecore.c @@ -5155,12 +5155,17 @@ const char *linphone_core_get_nat_address_resolved(LinphoneCore *lc) void linphone_core_set_firewall_policy(LinphoneCore *lc, LinphoneFirewallPolicy pol) { LinphoneNatPolicy *nat_policy; + char *stun_server = NULL; + char *stun_server_username = NULL; if (lc->nat_policy != NULL) { nat_policy = linphone_nat_policy_ref(lc->nat_policy); + stun_server = ms_strdup(linphone_nat_policy_get_stun_server(lc->nat_policy)); + stun_server_username = ms_strdup(linphone_nat_policy_get_stun_server_username(lc->nat_policy)); linphone_nat_policy_clear(nat_policy); } else { nat_policy = linphone_core_create_nat_policy(lc); + stun_server = ms_strdup(linphone_core_get_stun_server(lc)); } switch (pol) { @@ -5184,7 +5189,14 @@ void linphone_core_set_firewall_policy(LinphoneCore *lc, LinphoneFirewallPolicy break; } - linphone_nat_policy_set_stun_server(nat_policy, linphone_core_get_stun_server(lc)); + if (stun_server_username != NULL) { + linphone_nat_policy_set_stun_server_username(nat_policy, stun_server_username); + ms_free(stun_server_username); + } + if (stun_server != NULL) { + linphone_nat_policy_set_stun_server(nat_policy, stun_server); + ms_free(stun_server); + } linphone_core_set_nat_policy(lc, nat_policy); linphone_nat_policy_unref(nat_policy); } diff --git a/coreapi/misc.c b/coreapi/misc.c index 9e63a94e6..5cc467d67 100644 --- a/coreapi/misc.c +++ b/coreapi/misc.c @@ -637,18 +637,31 @@ void linphone_core_enable_forced_ice_relay(LinphoneCore *lc, bool_t enable) { static void stun_auth_requested_cb(LinphoneCall *call, const char *realm, const char *nonce, const char **username, const char **password, const char **ha1) { LinphoneProxyConfig *proxy = NULL; + const LinphoneNatPolicy *nat_policy = NULL; const LinphoneAddress *addr = NULL; const LinphoneAuthInfo *auth_info = NULL; LinphoneCore *lc = call->core; const char *user; - // Get the username from the proxy config + // Get the username from the nat policy or the proxy config if (call->dest_proxy != NULL) proxy = call->dest_proxy; else proxy = linphone_core_get_default_proxy_config(call->core); if (proxy == NULL) return; - addr = linphone_proxy_config_get_identity_address(proxy); - if (addr == NULL) return; - user = linphone_address_get_username(addr); + nat_policy = linphone_proxy_config_get_nat_policy(proxy); + if (nat_policy != NULL) { + user = linphone_nat_policy_get_stun_server_username(nat_policy); + } else { + nat_policy = linphone_core_get_nat_policy(call->core); + if (nat_policy != NULL) { + user = linphone_nat_policy_get_stun_server_username(nat_policy); + } + } + if (user == NULL) { + /* If the username has not been found in the nat_policy, take the username from the currently used proxy config. */ + addr = linphone_proxy_config_get_identity_address(proxy); + if (addr == NULL) return; + user = linphone_address_get_username(addr); + } if (user == NULL) return; auth_info = linphone_core_find_auth_info(lc, realm, user, NULL); diff --git a/coreapi/nat_policy.c b/coreapi/nat_policy.c index f28bf7985..9d172a0a0 100644 --- a/coreapi/nat_policy.c +++ b/coreapi/nat_policy.c @@ -38,6 +38,7 @@ static LinphoneNatPolicy * linphone_nat_policy_new(LinphoneCore *lc) { static void linphone_nat_policy_destroy(LinphoneNatPolicy *policy) { if (policy->ref) belle_sip_free(policy->ref); if (policy->stun_server) belle_sip_free(policy->stun_server); + if (policy->stun_server_username) belle_sip_free(policy->stun_server_username); if (policy->stun_addrinfo) freeaddrinfo(policy->stun_addrinfo); } @@ -66,6 +67,7 @@ static void _linphone_nat_policy_save_to_config(const LinphoneNatPolicy *policy, section = belle_sip_strdup_printf("nat_policy_%i", index); lp_config_set_string(config, section, "ref", policy->ref); lp_config_set_string(config, section, "stun_server", policy->stun_server); + lp_config_set_string(config, section, "stun_server_username", policy->stun_server_username); if (linphone_nat_policy_upnp_enabled(policy)) { l = ms_list_append(l, "upnp"); } else { @@ -183,6 +185,21 @@ void linphone_nat_policy_set_stun_server(LinphoneNatPolicy *policy, const char * } } +const char * linphone_nat_policy_get_stun_server_username(const LinphoneNatPolicy *policy) { + return policy->stun_server_username; +} + +void linphone_nat_policy_set_stun_server_username(LinphoneNatPolicy *policy, const char *username) { + char *new_username = NULL; + + if (username != NULL) new_username = belle_sip_strdup(username); + if (policy->stun_server_username != NULL) { + belle_sip_free(policy->stun_server_username); + policy->stun_server_username = NULL; + } + if (new_username != NULL) policy->stun_server_username = new_username; +} + static void stun_server_resolved(LinphoneNatPolicy *policy, const char *name, struct addrinfo *addrinfo) { if (policy->stun_addrinfo) { belle_sip_freeaddrinfo(policy->stun_addrinfo); @@ -259,9 +276,11 @@ LinphoneNatPolicy * linphone_core_create_nat_policy_from_config(LinphoneCore *lc const char *config_ref = lp_config_get_string(config, section, "ref", NULL); if ((config_ref != NULL) && (strcmp(config_ref, ref) == 0)) { const char *server = lp_config_get_string(config, section, "stun_server", NULL); + const char *username = lp_config_get_string(config, section, "stun_server_username", NULL); MSList *l = lp_config_get_string_list(config, section, "protocols", NULL); policy = _linphone_nat_policy_new_with_ref(lc, ref); if (server != NULL) linphone_nat_policy_set_stun_server(policy, server); + if (username != NULL) linphone_nat_policy_set_stun_server_username(policy, username); if (l != NULL) { bool_t upnp_enabled = FALSE; MSList *elem; diff --git a/coreapi/nat_policy.h b/coreapi/nat_policy.h index 96147ce67..e122508aa 100644 --- a/coreapi/nat_policy.h +++ b/coreapi/nat_policy.h @@ -131,7 +131,7 @@ LINPHONE_PUBLIC bool_t linphone_nat_policy_upnp_enabled(const LinphoneNatPolicy LINPHONE_PUBLIC void linphone_nat_policy_enable_upnp(LinphoneNatPolicy *policy, bool_t enable); /** - * Get the STUN server to use with this NAT policy. + * Get the STUN/TURN server to use with this NAT policy. * Used when STUN or TURN are enabled. * @param[in] policy LinphoneNatPolicy object * @return The STUN server used by this NAT policy. @@ -139,13 +139,31 @@ LINPHONE_PUBLIC void linphone_nat_policy_enable_upnp(LinphoneNatPolicy *policy, LINPHONE_PUBLIC const char * linphone_nat_policy_get_stun_server(const LinphoneNatPolicy *policy); /** - * Set the STUN server to use with this NAT policy. + * Set the STUN/TURN server to use with this NAT policy. * Used when STUN or TURN are enabled. * @param[in] policy LinphoneNatPolicy object * @param[in] stun_server The STUN server to use with this NAT policy. */ LINPHONE_PUBLIC void linphone_nat_policy_set_stun_server(LinphoneNatPolicy *policy, const char *stun_server); +/** + * Get the username used to authenticate with the STUN/TURN server. + * The authentication will search for a LinphoneAuthInfo with this username. + * If it is not set the username of the currently used LinphoneProxyConfig is used to search for a LinphoneAuthInfo. + * @param[in] policy LinphoneNatPolicy object + * @return The username used to authenticate with the STUN/TURN server. + */ +LINPHONE_PUBLIC const char * linphone_nat_policy_get_stun_server_username(const LinphoneNatPolicy *policy); + +/** + * Seth the username used to authenticate with the STUN/TURN server. + * The authentication will search for a LinphoneAuthInfo with this username. + * If it is not set the username of the currently used LinphoneProxyConfig is used to search for a LinphoneAuthInfo. + * @param[in] policy LinphoneNatPolicy object + * @param[in] username The username used to authenticate with the STUN/TURN server. + */ +LINPHONE_PUBLIC void linphone_nat_policy_set_stun_server_username(LinphoneNatPolicy *policy, const char *username); + /** * Start a STUN server DNS resolution. * @param[in] policy LinphoneNatPolicy object diff --git a/coreapi/private.h b/coreapi/private.h index 6d36cf6ed..365e0c9e4 100644 --- a/coreapi/private.h +++ b/coreapi/private.h @@ -1194,6 +1194,7 @@ struct _LinphoneNatPolicy { SalResolverContext *stun_resolver_context; struct addrinfo *stun_addrinfo; char *stun_server; + char *stun_server_username; char *ref; bool_t stun_enabled; bool_t turn_enabled;