Added configuration parameter "autostart" so MTP2, MTP3 and Cisco SLT may be inhibited at startup.

Fixed the way Cisco SLT notifies the MTP3 about alignment status changes.


git-svn-id: http://voip.null.ro/svn/yate@2810 acf43c95-373e-0410-b603-e72c3f656dc1
This commit is contained in:
paulc 2009-08-26 15:58:50 +00:00
parent 6e28715dea
commit 37059faf58
5 changed files with 56 additions and 33 deletions

View File

@ -60,6 +60,9 @@
; channel: int: Number of the channel inside the session, must match remote config ; channel: int: Number of the channel inside the session, must match remote config
;channel=0 ;channel=0
; autostart: bool: Automatically try to align the remote MTP2 at startup
;autostart=yes
; configuration: int: Configuration request retransmission interval in ms, 250+ ; configuration: int: Configuration request retransmission interval in ms, 250+
;configuration=5000 ;configuration=5000

View File

@ -353,6 +353,9 @@
; Example: route=ITU,2-2-2,0 ; Example: route=ITU,2-2-2,0
;route= ;route=
; autostart: bool: Automatically enable the linkset at startup
;autostart=yes
; layer3dump: string: Filename to dump MTP3 packets to ; layer3dump: string: Filename to dump MTP3 packets to
;layer3dump= ;layer3dump=
@ -365,6 +368,9 @@
; ss7-mtp2: SS7 Message Transfer Part - Layer 2 ; ss7-mtp2: SS7 Message Transfer Part - Layer 2
;type=ss7-mtp2 ;type=ss7-mtp2
; autostart: bool: Automatically try to align the MTP2 at startup
;autostart=yes
; emergency: boolean: Emergency align SS7 MTP2 layer at startup ; emergency: boolean: Emergency align SS7 MTP2 layer at startup
;emergency=yes ;emergency=yes

View File

@ -293,6 +293,7 @@ bool SS7MTP2::initialize(const NamedList* config)
if (config) if (config)
debugLevel(config->getIntValue("debuglevel_mtp2", debugLevel(config->getIntValue("debuglevel_mtp2",
config->getIntValue("debuglevel",-1))); config->getIntValue("debuglevel",-1)));
bool noStart = true;
if (config && !iface()) { if (config && !iface()) {
NamedString* name = config->getParam("sig"); NamedString* name = config->getParam("sig");
if (!name) if (!name)
@ -318,8 +319,9 @@ bool SS7MTP2::initialize(const NamedList* config)
if (!(ifc->initialize(ifConfig) && control((Operation)SignallingInterface::Enable,ifConfig))) if (!(ifc->initialize(ifConfig) && control((Operation)SignallingInterface::Enable,ifConfig)))
TelEngine::destruct(SignallingReceiver::attach(0)); TelEngine::destruct(SignallingReceiver::attach(0));
} }
noStart = !config->getBoolValue("autostart",true);
} }
return iface() && control(Resume,const_cast<NamedList*>(config)); return iface() && (noStart || control(Resume,const_cast<NamedList*>(config)));
} }
bool SS7MTP2::control(Operation oper, NamedList* params) bool SS7MTP2::control(Operation oper, NamedList* params)

View File

@ -387,6 +387,7 @@ SS7MTP3::SS7MTP3(const NamedList& params)
} }
Debug(this,level,"Point code types are '%s' [%p]",stype.safe(),this); Debug(this,level,"Point code types are '%s' [%p]",stype.safe(),this);
m_inhibit = !params.getBoolValue("autostart",true);
buildRoutes(params); buildRoutes(params);
setDumper(params.getValue("layer3dump")); setDumper(params.getValue("layer3dump"));
} }
@ -573,6 +574,7 @@ bool SS7MTP3::initialize(const NamedList* config)
TelEngine::destruct(link); TelEngine::destruct(link);
} }
} }
m_inhibit = !config->getBoolValue("autostart",true);
} }
if (engine() && !user()) { if (engine() && !user()) {
NamedList params("ss7router"); NamedList params("ss7router");
@ -615,9 +617,11 @@ int SS7MTP3::transmitMSU(const SS7MSU& msu, const SS7Label& label, int sls)
continue; continue;
SS7Layer2* link = *p; SS7Layer2* link = *p;
if (link->sls() == sls) { if (link->sls() == sls) {
DDebug(this,DebugAll,"Found link %p for SLS=%d [%p]",link,sls,this); XDebug(this,DebugAll,"Found link %p for SLS=%d [%p]",link,sls,this);
if (link->operational()) { if (link->operational()) {
if (link->transmitMSU(msu)) { if (link->transmitMSU(msu)) {
DDebug(this,DebugAll,"Sent MSU over link %p with SLS=%d%s [%p]",
link,sls,(m_inhibit ? " while inhibited" : ""),this);
dump(msu,true,sls); dump(msu,true,sls);
return sls; return sls;
} }
@ -636,8 +640,11 @@ int SS7MTP3::transmitMSU(const SS7MSU& msu, const SS7Label& label, int sls)
continue; continue;
SS7Layer2* link = *p; SS7Layer2* link = *p;
if (link->operational() && link->transmitMSU(msu)) { if (link->operational() && link->transmitMSU(msu)) {
dump(msu,true,link->sls()); sls = link->sls();
return link->sls(); DDebug(this,DebugAll,"Sent MSU over link %p with SLS=%d%s [%p]",
link,sls,(m_inhibit ? " while inhibited" : ""),this);
dump(msu,true,sls);
return sls;
} }
} }
@ -666,7 +673,8 @@ bool SS7MTP3::receivedMSU(const SS7MSU& msu, SS7Layer2* link, int sls)
if (debugAt(DebugInfo)) { if (debugAt(DebugInfo)) {
String tmp; String tmp;
tmp << label << " (" << label.opc().pack(cpType) << ":" << label.dpc().pack(cpType) << ":" << label.sls() << ")"; tmp << label << " (" << label.opc().pack(cpType) << ":" << label.dpc().pack(cpType) << ":" << label.sls() << ")";
Debug(this,DebugAll,"Received MSU. Address: %s",tmp.c_str()); Debug(this,DebugAll,"Received MSU from link %p with SLS=%d. Address: %s",
link,sls,tmp.c_str());
} }
#endif #endif
// first try to call the user part // first try to call the user part

View File

@ -376,7 +376,6 @@ public:
virtual ~SLT(); virtual ~SLT();
virtual unsigned int status() const; virtual unsigned int status() const;
void setStatus(unsigned int status); void setStatus(unsigned int status);
void setLocalStatus(unsigned int status);
void setRemoteStatus(unsigned int status); void setRemoteStatus(unsigned int status);
void setReqStatus(unsigned int status); void setReqStatus(unsigned int status);
virtual void notify(bool up); virtual void notify(bool up);
@ -424,7 +423,6 @@ public:
static SignallingComponent* create(const String& type,const NamedList& params); static SignallingComponent* create(const String& type,const NamedList& params);
protected: protected:
unsigned int m_status; // Layer status unsigned int m_status; // Layer status
unsigned int m_lStatus; // Local layer status
unsigned int m_rStatus; // Remote layer status unsigned int m_rStatus; // Remote layer status
unsigned int m_reqStatus; // We keep the requested status and we change it when unsigned int m_reqStatus; // We keep the requested status and we change it when
// receive the confirmation // receive the confirmation
@ -1537,9 +1535,10 @@ const TokenDict SLT::s_protocolError[] = {
}; };
SLT::SLT(const String& name, const NamedList& param) SLT::SLT(const String& name, const NamedList& param)
: SignallingComponent(param.safe("CiscoSLT")), SessionUser(1), : SignallingComponent(param.safe("CiscoSLT")),
m_status(Unconfigured), m_lStatus(NormalAlignment), m_rStatus(OutOfAlignment), SessionUser(1),
m_reqStatus(NormalAlignment), m_messageId(1), m_channelId(0), m_bearerId(0), m_status(Unconfigured), m_rStatus(OutOfService), m_reqStatus(OutOfService),
m_messageId(1), m_channelId(0), m_bearerId(0),
m_confReqTimer(0), m_printMsg(false) m_confReqTimer(0), m_printMsg(false)
{ {
m_channelId = param.getIntValue("channel",0); m_channelId = param.getIntValue("channel",0);
@ -1552,6 +1551,8 @@ SLT::SLT(const String& name, const NamedList& param)
} }
m_confReqTimer.interval(param,"configuration",250,5000,true); m_confReqTimer.interval(param,"configuration",250,5000,true);
m_printMsg = param.getBoolValue("printslt",false); m_printMsg = param.getBoolValue("printslt",false);
if (param.getBoolValue("autostart",true))
m_reqStatus = NormalAlignment;
} }
SLT::~SLT() SLT::~SLT()
@ -1581,22 +1582,16 @@ void SLT::setStatus(unsigned int status)
m_status = status; m_status = status;
} }
void SLT::setLocalStatus(unsigned int status)
{
if (status == m_lStatus)
return;
DDebug(this,DebugNote,"Local status change: %s -> %s [%p]",
statusName(m_lStatus,true),statusName(status,true),this);
m_lStatus = status;
}
void SLT::setRemoteStatus(unsigned int status) void SLT::setRemoteStatus(unsigned int status)
{ {
if (status == m_rStatus) if (status == m_rStatus)
return; return;
DDebug(this,DebugNote,"Remote status change: %s -> %s [%p]", DDebug(this,DebugNote,"Remote status change: %s -> %s [%p]",
statusName(m_rStatus,true),statusName(status,true),this); statusName(m_rStatus,true),statusName(status,true),this);
bool old = aligned();
m_rStatus = status; m_rStatus = status;
if (aligned() != old)
SS7Layer2::notify();
} }
void SLT::setReqStatus(unsigned int status) void SLT::setReqStatus(unsigned int status)
@ -1605,7 +1600,10 @@ void SLT::setReqStatus(unsigned int status)
return; return;
DDebug(this,DebugNote,"Request status change: %s -> %s [%p]", DDebug(this,DebugNote,"Request status change: %s -> %s [%p]",
statusName(m_reqStatus,true),statusName(status,true),this); statusName(m_reqStatus,true),statusName(status,true),this);
bool old = aligned();
m_reqStatus = status; m_reqStatus = status;
if (aligned() != old)
SS7Layer2::notify();
} }
// Process notification received from session manager // Process notification received from session manager
@ -1622,7 +1620,6 @@ void SLT::notify(bool up)
bool SLT::control(Operation oper, NamedList* params) bool SLT::control(Operation oper, NamedList* params)
{ {
bool normal = true;
switch (oper) { switch (oper) {
case Pause: case Pause:
setReqStatus(OutOfService); setReqStatus(OutOfService);
@ -1632,11 +1629,21 @@ bool SLT::control(Operation oper, NamedList* params)
if (aligned()) if (aligned())
return true; return true;
case Align: case Align:
normal = !params->getBoolValue("emergency",false); {
sendConnect(normal ? Emergency : Normal); bool emg = params->getBoolValue("emergency");
setReqStatus(normal ? EmergencyAlignment : NormalAlignment); setReqStatus(emg ? EmergencyAlignment : NormalAlignment);
setLocalStatus(NormalAlignment); switch (m_status) {
setStatus(Waiting); case Configured:
sendConnect(emg ? Emergency : Normal);
break;
case Waiting:
break;
default:
sendManagement(Configuration_R);
m_confReqTimer.start();
setStatus(Waiting);
}
}
return true; return true;
case Status: case Status:
return aligned() && m_status == Configured; return aligned() && m_status == Configured;
@ -1647,7 +1654,7 @@ bool SLT::control(Operation oper, NamedList* params)
bool SLT::aligned() const bool SLT::aligned() const
{ {
return ((m_lStatus == NormalAlignment) || (m_lStatus == EmergencyAlignment)) && return ((m_reqStatus == NormalAlignment) || (m_reqStatus == EmergencyAlignment)) &&
((m_rStatus == NormalAlignment) || (m_rStatus == EmergencyAlignment)); ((m_rStatus == NormalAlignment) || (m_rStatus == EmergencyAlignment));
} }
@ -1746,8 +1753,8 @@ bool SLT::checkMessage(DataBlock& data)
SS7MSU msu(data); SS7MSU msu(data);
return receivedMSU(msu); return receivedMSU(msu);
} else } else
DDebug(this,DebugWarn,"Received data message but we are not aligned local status = %s,remote status = %s", DDebug(this,DebugWarn,"Received data message while not aligned, local status = %s, remote status = %s",
statusName(m_lStatus,false),statusName(m_rStatus,false)); statusName(m_reqStatus,false),statusName(m_rStatus,false));
} else if (msgType & 0x40) { } else if (msgType & 0x40) {
data.cut(-16); // Management message data.cut(-16); // Management message
processManagement(msgType,data); processManagement(msgType,data);
@ -1801,16 +1808,15 @@ void SLT::processSltMessage(u_int16_t msgType, DataBlock& data)
setRemoteStatus(mes == Normal ? NormalAlignment : EmergencyAlignment); setRemoteStatus(mes == Normal ? NormalAlignment : EmergencyAlignment);
if (aligned()) if (aligned())
m_session->userNotice(true); m_session->userNotice(true);
SS7Layer2::notify();
} }
break; break;
case Disconnect_C: case Disconnect_C:
setRemoteStatus(OutOfService);
if (m_reqStatus == EmergencyAlignment || m_reqStatus == NormalAlignment) if (m_reqStatus == EmergencyAlignment || m_reqStatus == NormalAlignment)
sendConnect(m_reqStatus == NormalAlignment ? Normal : Emergency); sendConnect(m_reqStatus == NormalAlignment ? Normal : Emergency);
else
setRemoteStatus(m_reqStatus);
break; break;
case Disconnect_I: case Disconnect_I:
setRemoteStatus(OutOfService);
if (m_reqStatus == EmergencyAlignment || m_reqStatus == NormalAlignment) if (m_reqStatus == EmergencyAlignment || m_reqStatus == NormalAlignment)
sendConnect(m_reqStatus == NormalAlignment ? Normal : Emergency); sendConnect(m_reqStatus == NormalAlignment ? Normal : Emergency);
break; break;
@ -1818,7 +1824,6 @@ void SLT::processSltMessage(u_int16_t msgType, DataBlock& data)
setRemoteStatus(m_reqStatus); setRemoteStatus(m_reqStatus);
if (aligned()) if (aligned())
m_session->userNotice(false); m_session->userNotice(false);
SS7Layer2::notify();
break; break;
case Link_State_Controller_I: case Link_State_Controller_I:
processCIndication(data); processCIndication(data);
@ -1961,7 +1966,6 @@ bool SLT::transmitMSU(const SS7MSU& msu)
return false; return false;
if (!aligned()) { if (!aligned()) {
Debug(this,DebugNote,"Requested to send data while not operational"); Debug(this,DebugNote,"Requested to send data while not operational");
SS7Layer2::notify();
return false; return false;
} }
DataBlock data; DataBlock data;