Try to bind the IAX socket on a random port if failed to bind on configured one. Fixed socket read/write error reporting.
git-svn-id: http://voip.null.ro/svn/yate@4474 acf43c95-373e-0410-b603-e72c3f656dc1
This commit is contained in:
parent
41dfba4982
commit
77bf052e18
|
@ -7,6 +7,10 @@
|
||||||
; addr: ipaddress: IP address to bind to
|
; addr: ipaddress: IP address to bind to
|
||||||
;addr=0.0.0.0
|
;addr=0.0.0.0
|
||||||
|
|
||||||
|
; force_bind: boolean: Try to use a random port if failed to bind on configured one
|
||||||
|
; Defaults to yes
|
||||||
|
;force_bind=yes
|
||||||
|
|
||||||
; tos: keyword: Type Of Service to set in outgoing UDP packets
|
; tos: keyword: Type Of Service to set in outgoing UDP packets
|
||||||
; numeric TOS value or: lowdelay, throughput, reliability, mincost
|
; numeric TOS value or: lowdelay, throughput, reliability, mincost
|
||||||
;tos=0
|
;tos=0
|
||||||
|
|
|
@ -32,7 +32,8 @@ using namespace TelEngine;
|
||||||
|
|
||||||
IAXEngine::IAXEngine(const char* iface, int port, u_int16_t transListCount, u_int16_t retransCount, u_int16_t retransInterval,
|
IAXEngine::IAXEngine(const char* iface, int port, u_int16_t transListCount, u_int16_t retransCount, u_int16_t retransInterval,
|
||||||
u_int16_t authTimeout, u_int16_t transTimeout, u_int16_t maxFullFrameDataLen,
|
u_int16_t authTimeout, u_int16_t transTimeout, u_int16_t maxFullFrameDataLen,
|
||||||
u_int32_t format, u_int32_t capab, u_int32_t trunkSendInterval, bool authRequired)
|
u_int32_t format, u_int32_t capab, u_int32_t trunkSendInterval, bool authRequired,
|
||||||
|
NamedList* params)
|
||||||
: Mutex(true,"IAXEngine"),
|
: Mutex(true,"IAXEngine"),
|
||||||
m_lastGetEvIndex(0),
|
m_lastGetEvIndex(0),
|
||||||
m_authRequired(authRequired),
|
m_authRequired(authRequired),
|
||||||
|
@ -69,8 +70,28 @@ IAXEngine::IAXEngine(const char* iface, int port, u_int16_t transListCount, u_in
|
||||||
addr.host(iface);
|
addr.host(iface);
|
||||||
addr.port(port);
|
addr.port(port);
|
||||||
m_socket.setBlocking(false);
|
m_socket.setBlocking(false);
|
||||||
if (!m_socket.bind(addr))
|
bool ok = m_socket.bind(addr);
|
||||||
Debug(this,DebugWarn,"Failed to bind socket to %s:%d",c_safe(iface),port);
|
if (!ok) {
|
||||||
|
bool force = !params || params->getBoolValue("force_bind",true);
|
||||||
|
String tmp;
|
||||||
|
Thread::errorString(tmp,m_socket.error());
|
||||||
|
Debug(this,DebugWarn,"Failed to bind socket on '%s:%d'%s. %d: '%s'",
|
||||||
|
c_safe(iface),port,force ? " - trying a random port" : "",
|
||||||
|
m_socket.error(),tmp.c_str());
|
||||||
|
if (force) {
|
||||||
|
addr.port(0);
|
||||||
|
ok = m_socket.bind(addr);
|
||||||
|
if (!ok)
|
||||||
|
Debug(this,DebugWarn,"Failed to bind on any port");
|
||||||
|
else {
|
||||||
|
ok = m_socket.getSockName(addr);
|
||||||
|
if (!ok)
|
||||||
|
Debug(this,DebugWarn,"Failed to retrieve bound address");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (ok)
|
||||||
|
Debug(this,DebugInfo,"Bound on '%s:%d'",addr.host().c_str(),addr.port());
|
||||||
m_startLocalCallNo = 1 + (u_int16_t)(Random::random() % IAX2_MAX_CALLNO);
|
m_startLocalCallNo = 1 + (u_int16_t)(Random::random() % IAX2_MAX_CALLNO);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -219,9 +240,12 @@ void IAXEngine::readSocket(SocketAddr& addr)
|
||||||
while (1) {
|
while (1) {
|
||||||
int len = m_socket.recvFrom(buf,sizeof(buf),addr);
|
int len = m_socket.recvFrom(buf,sizeof(buf),addr);
|
||||||
if (len == Socket::socketError()) {
|
if (len == Socket::socketError()) {
|
||||||
if (!m_socket.canRetry())
|
if (!m_socket.canRetry()) {
|
||||||
|
String tmp;
|
||||||
|
Thread::errorString(tmp,m_socket.error());
|
||||||
Debug(this,DebugWarn,"Socket read error: %s (%d)",
|
Debug(this,DebugWarn,"Socket read error: %s (%d)",
|
||||||
::strerror(m_socket.error()),m_socket.error());
|
tmp.c_str(),m_socket.error());
|
||||||
|
}
|
||||||
Thread::idle(true);
|
Thread::idle(true);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -240,9 +264,12 @@ bool IAXEngine::writeSocket(const void* buf, int len, const SocketAddr& addr, IA
|
||||||
}
|
}
|
||||||
len = m_socket.sendTo(buf,len,addr);
|
len = m_socket.sendTo(buf,len,addr);
|
||||||
if (len == Socket::socketError()) {
|
if (len == Socket::socketError()) {
|
||||||
if (!m_socket.canRetry())
|
if (!m_socket.canRetry()) {
|
||||||
|
String tmp;
|
||||||
|
Thread::errorString(tmp,m_socket.error());
|
||||||
Debug(this,DebugWarn,"Socket write error: %s (%d)",
|
Debug(this,DebugWarn,"Socket write error: %s (%d)",
|
||||||
::strerror(m_socket.error()),m_socket.error());
|
tmp.c_str(),m_socket.error());
|
||||||
|
}
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
else
|
else
|
||||||
Debug(this,DebugMild,"Socket temporary unavailable: %s (%d)",
|
Debug(this,DebugMild,"Socket temporary unavailable: %s (%d)",
|
||||||
|
|
|
@ -2036,10 +2036,12 @@ public:
|
||||||
* @param capab Media capabilities of this engine
|
* @param capab Media capabilities of this engine
|
||||||
* @param trunkSendInterval Send trunk meta frame interval
|
* @param trunkSendInterval Send trunk meta frame interval
|
||||||
* @param authRequired Automatically challenge all clients for authentication
|
* @param authRequired Automatically challenge all clients for authentication
|
||||||
|
* @param params Optional extra parameter list
|
||||||
*/
|
*/
|
||||||
IAXEngine(const char* iface, int port, u_int16_t transListCount, u_int16_t retransCount, u_int16_t retransInterval,
|
IAXEngine(const char* iface, int port, u_int16_t transListCount, u_int16_t retransCount, u_int16_t retransInterval,
|
||||||
u_int16_t authTimeout, u_int16_t transTimeout, u_int16_t maxFullFrameDataLen,
|
u_int16_t authTimeout, u_int16_t transTimeout, u_int16_t maxFullFrameDataLen,
|
||||||
u_int32_t format, u_int32_t capab, u_int32_t trunkSendInterval, bool authRequired);
|
u_int32_t format, u_int32_t capab, u_int32_t trunkSendInterval, bool authRequired,
|
||||||
|
NamedList* params = 0);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Destructor
|
* Destructor
|
||||||
|
|
|
@ -263,7 +263,8 @@ public:
|
||||||
*/
|
*/
|
||||||
YIAXEngine(const char* iface, int port, u_int16_t transListCount, u_int16_t retransCount, u_int16_t retransInterval,
|
YIAXEngine(const char* iface, int port, u_int16_t transListCount, u_int16_t retransCount, u_int16_t retransInterval,
|
||||||
u_int16_t authTimeout, u_int16_t transTimeout,
|
u_int16_t authTimeout, u_int16_t transTimeout,
|
||||||
u_int16_t maxFullFrameDataLen, u_int32_t trunkSendInterval, bool authRequired);
|
u_int16_t maxFullFrameDataLen, u_int32_t trunkSendInterval, bool authRequired,
|
||||||
|
NamedList* params);
|
||||||
|
|
||||||
virtual ~YIAXEngine()
|
virtual ~YIAXEngine()
|
||||||
{}
|
{}
|
||||||
|
@ -944,10 +945,10 @@ void YIAXTrunking::run()
|
||||||
YIAXEngine::YIAXEngine(const char* iface, int port, u_int16_t transListCount,
|
YIAXEngine::YIAXEngine(const char* iface, int port, u_int16_t transListCount,
|
||||||
u_int16_t retransCount, u_int16_t retransInterval, u_int16_t authTimeout,
|
u_int16_t retransCount, u_int16_t retransInterval, u_int16_t authTimeout,
|
||||||
u_int16_t transTimeout, u_int16_t maxFullFrameDataLen,
|
u_int16_t transTimeout, u_int16_t maxFullFrameDataLen,
|
||||||
u_int32_t trunkSendInterval, bool authRequired)
|
u_int32_t trunkSendInterval, bool authRequired, NamedList* params)
|
||||||
: IAXEngine(iface,port,transListCount,retransCount,retransInterval,authTimeout,
|
: IAXEngine(iface,port,transListCount,retransCount,retransInterval,authTimeout,
|
||||||
transTimeout,maxFullFrameDataLen,iplugin.defaultCodec(),iplugin.codecs(),
|
transTimeout,maxFullFrameDataLen,iplugin.defaultCodec(),iplugin.codecs(),
|
||||||
trunkSendInterval,authRequired),
|
trunkSendInterval,authRequired,params),
|
||||||
m_threadsCreated(false)
|
m_threadsCreated(false)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
@ -1250,7 +1251,7 @@ void YIAXDriver::initialize()
|
||||||
String iface = s_cfg.getValue("general","addr");
|
String iface = s_cfg.getValue("general","addr");
|
||||||
bool authReq = s_cfg.getBoolValue("registrar","auth_required",true);
|
bool authReq = s_cfg.getBoolValue("registrar","auth_required",true);
|
||||||
m_iaxEngine = new YIAXEngine(iface,m_port,transListCount,retransCount,retransInterval,authTimeout,
|
m_iaxEngine = new YIAXEngine(iface,m_port,transListCount,retransCount,retransInterval,authTimeout,
|
||||||
transTimeout,maxFullFrameDataLen,trunkSendInterval,authReq);
|
transTimeout,maxFullFrameDataLen,trunkSendInterval,authReq,s_cfg.getSection("general"));
|
||||||
m_iaxEngine->debugChain(this);
|
m_iaxEngine->debugChain(this);
|
||||||
int tos = s_cfg.getIntValue("general","tos",dict_tos,0);
|
int tos = s_cfg.getIntValue("general","tos",dict_tos,0);
|
||||||
if (tos && !m_iaxEngine->socket().setTOS(tos))
|
if (tos && !m_iaxEngine->socket().setTOS(tos))
|
||||||
|
|
Loading…
Reference in New Issue