Commit 62898a7d authored by Tristan Matthews's avatar Tristan Matthews

* #14077: sip: check if server address in SIP transactions is our proxy

parent dcb80d4e
......@@ -2669,7 +2669,8 @@ ManagerImpl::getAccount(const std::string& accountID)
return accountMap_[SIPAccount::IP2IP_PROFILE];
}
std::string ManagerImpl::getAccountIdFromNameAndServer(const std::string& userName, const std::string& server) const
std::string
ManagerImpl::getAccountIdFromNameAndServer(const std::string& userName, const std::string& server) const
{
DEBUG("username = %s, server = %s", userName.c_str(), server.c_str());
// Try to find the account id from username and server name by full match
......@@ -2703,6 +2704,16 @@ std::string ManagerImpl::getAccountIdFromNameAndServer(const std::string& userNa
}
}
// We failed! Then only match the hostname against our proxy
for (AccountMap::const_iterator iter = accountMap_.begin(); iter != accountMap_.end(); ++iter) {
SIPAccount *account = dynamic_cast<SIPAccount *>(iter->second);
if (account and account->isEnabled() and account->proxyMatch(server)) {
DEBUG("Matching account id in request with proxy %s", server.c_str());
return iter->first;
}
}
DEBUG("Username %s or server %s doesn't match any account, using IP2IP", userName.c_str(), server.c_str());
return "";
}
......
......@@ -42,6 +42,13 @@
#include <pj/list.h>
#include "sip_utils.h"
// for resolveDns
#include <list>
#include <netdb.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
std::string
sip_utils::fetchHeaderValue(pjsip_msg *msg, const std::string &field)
{
......@@ -124,3 +131,41 @@ sip_utils::stripSipUriPrefix(std::string& sipUri)
if (found != std::string::npos)
sipUri.erase(found);
}
/**
* This function looks for '@' and replaces the second part with the corresponding ip address (when possible)
*/
std::string
sip_utils::resolveDns(const std::string &url)
{
size_t pos;
if ((pos = url.find("@")) == std::string::npos)
return url;
const std::string hostname = url.substr(pos + 1);
std::list<std::string> ipList(resolveServerDns(hostname));
if (not ipList.empty() and ipList.front().size() > 7 )
return url.substr(0, pos + 1) + ipList.front();
else
return hostname;
}
/**
* This function finds the list of IP addresses (when possible) for a given server
*/
std::list<std::string>
sip_utils::resolveServerDns(const std::string &server)
{
struct hostent *he;
std::list<std::string> ipList;
if ((he = gethostbyname(server.c_str())) == NULL)
return ipList;
struct in_addr **addr_list = (struct in_addr **) he->h_addr_list;
for (int i = 0; addr_list[i] != NULL; ++i)
ipList.push_back(inet_ntoa(*addr_list[i]));
return ipList;
}
......@@ -33,6 +33,7 @@
#define SIP_UTILS_H_
#include <string>
#include <list>
#include <pjsip/sip_msg.h>
......@@ -50,6 +51,9 @@ namespace sip_utils {
void stripSipUriPrefix(std::string& sipUri);
std::string parseDisplayName(const char * buffer);
std::string resolveDns(const std::string &url);
std::list<std::string> resolveServerDns(const std::string &server);
}
#endif // SIP_UTILS_H_
......@@ -36,6 +36,7 @@
#include "account_schema.h"
#include "sipaccount.h"
#include "sip_utils.h"
#include "sipvoiplink.h"
#include "config/yamlnode.h"
#include "config/yamlemitter.h"
......@@ -43,7 +44,8 @@
#include "manager.h"
#include <pwd.h>
#include <sstream>
#include <stdlib.h>
#include <algorithm>
#include <cstdlib>
#ifdef SFL_VIDEO
#include "video/libav_utils.h"
......@@ -794,6 +796,14 @@ bool SIPAccount::hostnameMatch(const std::string& hostname) const
return hostname == hostname_;
}
bool SIPAccount::proxyMatch(const std::string& hostname) const
{
if (hostname == serviceRoute_)
return true;
const std::list<std::string> ipList(sip_utils::resolveServerDns(serviceRoute_));
return std::find(ipList.begin(), ipList.end(), hostname) != ipList.end();
}
std::string SIPAccount::getLoginName()
{
struct passwd * user_info = getpwuid(getuid());
......
......@@ -250,6 +250,7 @@ class SIPAccount : public Account {
bool fullMatch(const std::string& username, const std::string& hostname) const;
bool userMatch(const std::string& username) const;
bool hostnameMatch(const std::string& hostname) const;
bool proxyMatch(const std::string& hostname) const;
/**
* Registration flag
......
......@@ -725,43 +725,12 @@ bool isValidIpAddress(const std::string &address)
return result != 0;
}
/**
* This function look for '@' and replace the second part with the corresponding ip address (when possible)
*/
std::string resolvDns(const std::string& url)
{
size_t pos;
if ((pos = url.find("@")) == std::string::npos) {
return url;
}
std::string hostname = url.substr(pos+1);
int i;
struct hostent *he;
struct in_addr **addr_list;
if ((he = gethostbyname(hostname.c_str())) == NULL) {
return url;
}
addr_list = (struct in_addr **)he->h_addr_list;
std::list<std::string> ipList;
for(i = 0; addr_list[i] != NULL; i++) {
ipList.push_back(inet_ntoa(*addr_list[i]));
}
if (ipList.size() > 0 && ipList.front().size() > 7 )
return url.substr(0,pos+1)+ipList.front();
else
return hostname;
}
Call *SIPVoIPLink::newOutgoingCall(const std::string& id, const std::string& toUrl)
{
DEBUG("New outgoing call to %s", toUrl.c_str());
std::string toCpy = toUrl;
std::string resolvedUrl = resolvDns(toUrl);
std::string resolvedUrl = sip_utils::resolveDns(toUrl);
DEBUG("URL resolved to %s", resolvedUrl.c_str());
sip_utils::stripSipUriPrefix(toCpy);
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment