From 811e950e91f70fb1226405ee826ae4d466e138ea Mon Sep 17 00:00:00 2001 From: Tom Early Date: Fri, 3 Jul 2020 10:50:59 -0700 Subject: [PATCH] CClients::m_Clients is a list --- src/cclients.cpp | 248 +++++++++++++++----------------------- src/cclients.h | 30 +++-- src/cdcsprotocol.cpp | 99 +++++++-------- src/cdextraprotocol.cpp | 14 +-- src/cdmrmmdvmprotocol.cpp | 216 ++++++++++++++++----------------- src/cdmrplusprotocol.cpp | 117 +++++++++--------- src/cdplusprotocol.cpp | 101 ++++++++-------- src/cg3protocol.cpp | 73 ++++++----- src/creflector.cpp | 62 +++++----- src/cxlxprotocol.cpp | 4 +- src/cysfprotocol.cpp | 135 +++++++++++---------- 11 files changed, 524 insertions(+), 575 deletions(-) diff --git a/src/cclients.cpp b/src/cclients.cpp index 837802a..f34e4c8 100644 --- a/src/cclients.cpp +++ b/src/cclients.cpp @@ -4,6 +4,7 @@ // // Created by Jean-Luc Deltombe (LX3JL) on 31/10/2015. // Copyright © 2015 Jean-Luc Deltombe (LX3JL). All rights reserved. +// Copyright © 2020 Thomas A. Early, N7TAE // // ---------------------------------------------------------------------------- // This file is part of xlxd. @@ -19,7 +20,7 @@ // GNU General Public License for more details. // // You should have received a copy of the GNU General Public License -// along with Foobar. If not, see . +// along with Foobar. If not, see . // ---------------------------------------------------------------------------- #include "main.h" @@ -33,7 +34,6 @@ CClients::CClients() { - m_Clients.reserve(100); } //////////////////////////////////////////////////////////////////////////////////////// @@ -42,14 +42,11 @@ CClients::CClients() CClients::~CClients() { m_Mutex.lock(); - { - for ( int i = 0; i < m_Clients.size(); i++ ) - { - delete m_Clients[i]; - } - m_Clients.clear(); - - } + for ( auto it=begin(); it!=end(); it++ ) + { + delete *it; + } + m_Clients.clear(); m_Mutex.unlock(); } @@ -59,93 +56,69 @@ CClients::~CClients() void CClients::AddClient(CClient *client) { // first check if client already exists - bool found = false; - for ( int i = 0; (i < m_Clients.size()) && !found; i++ ) + for ( auto it=begin(); it!=end(); it++ ) { - found = (*client == *m_Clients[i]); + if (*client == *(*it)) // if found, just do nothing // so *client keep pointing on a valid object // on function return - if ( found ) { // delete new one delete client; - //std::cout << "Adding existing client " << client->GetCallsign() << " at " << client->GetIp() << std::endl; + return; } } - - // if not, append to the vector - if ( !found ) - { - // grow vector capacity if needed - if ( m_Clients.capacity() == m_Clients.size() ) - { - m_Clients.reserve(m_Clients.capacity()+10); - } - // and append - m_Clients.push_back(client); - std::cout << "New client " << client->GetCallsign() << " at " << client->GetIp() - << " added with protocol " << client->GetProtocolName(); - if ( client->GetReflectorModule() != ' ' ) - { - std::cout << " on module " << client->GetReflectorModule(); - } - std::cout << std::endl; - // notify - g_Reflector.OnClientsChanged(); - } + + // and append + m_Clients.push_back(client); + std::cout << "New client " << client->GetCallsign() << " at " << client->GetIp() + << " added with protocol " << client->GetProtocolName(); + if ( client->GetReflectorModule() != ' ' ) + { + std::cout << " on module " << client->GetReflectorModule(); + } + std::cout << std::endl; + // notify + g_Reflector.OnClientsChanged(); } void CClients::RemoveClient(CClient *client) -{ +{ // look for the client bool found = false; - for ( int i = 0; (i < m_Clients.size()) && !found; i++ ) + for ( auto it=begin(); it!=end(); it++ ) { // compare objetc pointers - if ( (m_Clients[i]) == client ) + if ( *it == client ) { // found it ! - if ( !m_Clients[i]->IsAMaster() ) + if ( !(*it)->IsAMaster() ) { // remove it - std::cout << "Client " << m_Clients[i]->GetCallsign() << " at " << m_Clients[i]->GetIp() - << " removed with protocol " << client->GetProtocolName(); - if ( client->GetReflectorModule() != ' ' ) + std::cout << "Client " << (*it)->GetCallsign() << " at " << (*it)->GetIp() << " removed with protocol " << (*it)->GetProtocolName(); + if ( (*it)->GetReflectorModule() != ' ' ) { - std::cout << " on module " << client->GetReflectorModule(); + std::cout << " on module " << (*it)->GetReflectorModule(); } std::cout << std::endl; - delete m_Clients[i]; - m_Clients.erase(m_Clients.begin()+i); - found = true; + delete *it; + m_Clients.erase(it); // notify g_Reflector.OnClientsChanged(); + break; } } } } -CClient *CClients::GetClient(int i) -{ - if ( (i >= 0) && (i < m_Clients.size()) ) - { - return m_Clients[i]; - } - else - { - return NULL; - } -} - bool CClients::IsClient(CClient *client) const { - bool found = false; - for ( int i = 0; (i < m_Clients.size()) && !found; i++ ) + for ( auto it=cbegin(); it!=cend(); it++ ) { - found = (m_Clients[i] == client); + if (*it == client) + return true; } - return found; + return false; } //////////////////////////////////////////////////////////////////////////////////////// @@ -153,171 +126,140 @@ bool CClients::IsClient(CClient *client) const CClient *CClients::FindClient(const CIp &Ip) { - CClient *client = NULL; - // find client - for ( int i = 0; (i < m_Clients.size()) && (client == NULL); i++ ) + for ( auto it=begin(); it!=end(); it++ ) { - if ( m_Clients[i]->GetIp() == Ip ) + if ( (*it)->GetIp() == Ip ) { - client = m_Clients[i]; + return *it; } } - + // done - return client; + return NULL; } CClient *CClients::FindClient(const CIp &Ip, int Protocol) { - CClient *client = NULL; - // find client - for ( int i = 0; (i < m_Clients.size()) && (client == NULL); i++ ) + for ( auto it=begin(); it!=end(); it++ ) { - if ( (m_Clients[i]->GetIp() == Ip) && (m_Clients[i]->GetProtocol() == Protocol)) + if ( ((*it)->GetIp() == Ip) && ((*it)->GetProtocol() == Protocol)) { - client = m_Clients[i]; + return *it; } } - + // done - return client; + return NULL; } CClient *CClients::FindClient(const CIp &Ip, int Protocol, char ReflectorModule) { - CClient *client = NULL; - // find client - for ( int i = 0; (i < m_Clients.size()) && (client == NULL); i++ ) + for ( auto it=begin(); it!=end(); it++ ) { - if ( (m_Clients[i]->GetIp() == Ip) && - (m_Clients[i]->GetReflectorModule() == ReflectorModule) && - (m_Clients[i]->GetProtocol() == Protocol) ) + if ( ((*it)->GetIp() == Ip) && + ((*it)->GetReflectorModule() == ReflectorModule) && + ((*it)->GetProtocol() == Protocol) ) { - client = m_Clients[i]; + return *it; } } - + // done - return client; + return NULL; } CClient *CClients::FindClient(const CCallsign &Callsign, const CIp &Ip, int Protocol) { - CClient *client = NULL; - // find client - for ( int i = 0; (i < m_Clients.size()) && (client == NULL); i++ ) + for ( auto it=begin(); it!=end(); it++ ) { - if ( m_Clients[i]->GetCallsign().HasSameCallsign(Callsign) && - (m_Clients[i]->GetIp() == Ip) && - (m_Clients[i]->GetProtocol() == Protocol) ) + if ( (*it)->GetCallsign().HasSameCallsign(Callsign) && + ((*it)->GetIp() == Ip) && + ((*it)->GetProtocol() == Protocol) ) { - client = m_Clients[i]; + return *it; } } - - // done - return client; + + return NULL; } CClient *CClients::FindClient(const CCallsign &Callsign, char module, const CIp &Ip, int Protocol) { - CClient *client = NULL; - // find client - for ( int i = 0; (i < m_Clients.size()) && (client == NULL); i++ ) + for ( auto it=begin(); it!=end(); it++ ) { - if ( m_Clients[i]->GetCallsign().HasSameCallsign(Callsign) && - (m_Clients[i]->GetModule() == module) && - (m_Clients[i]->GetIp() == Ip) && - (m_Clients[i]->GetProtocol() == Protocol) ) + if ( (*it)->GetCallsign().HasSameCallsign(Callsign) && + ((*it)->GetModule() == module) && + ((*it)->GetIp() == Ip) && + ((*it)->GetProtocol() == Protocol) ) { - client = m_Clients[i]; + return *it; } } - - // done - return client; + + return NULL; } CClient *CClients::FindClient(const CCallsign &Callsign, int Protocol) { - CClient *client = NULL; - // find client - for ( int i = 0; (i < m_Clients.size()) && (client == NULL); i++ ) + for ( auto it=begin(); it!=end(); it++ ) { - if ( (m_Clients[i]->GetProtocol() == Protocol) && - m_Clients[i]->GetCallsign().HasSameCallsign(Callsign) ) + if ( ((*it)->GetProtocol() == Protocol) && + (*it)->GetCallsign().HasSameCallsign(Callsign) ) { - client = m_Clients[i]; + return *it; } } - - // done - return client; + + return NULL; } //////////////////////////////////////////////////////////////////////////////////////// // iterate on clients -CClient *CClients::FindNextClient(int Protocol, int *index) +CClient *CClients::FindNextClient(int Protocol, std::list::iterator &it) { - CClient *client = NULL; - - // find next client - bool found = false; - for ( int i = *index+1; (i < m_Clients.size()) && !found; i++ ) + while ( it != end() ) { - if ( m_Clients[i]->GetProtocol() == Protocol ) + if ( (*it)->GetProtocol() == Protocol ) { - found = true; - client = m_Clients[i]; - *index = i; + return *it++; } + it++; } - return client; + return NULL; } -CClient *CClients::FindNextClient(const CIp &Ip, int Protocol, int *index) +CClient *CClients::FindNextClient(const CIp &Ip, int Protocol, std::list::iterator &it) { - CClient *client = NULL; - - // find next client - bool found = false; - for ( int i = *index+1; (i < m_Clients.size()) && !found; i++ ) + while ( it != end() ) { - if ( (m_Clients[i]->GetProtocol() == Protocol) && - (m_Clients[i]->GetIp() == Ip) ) + if ( ((*it)->GetProtocol() == Protocol) && + ((*it)->GetIp() == Ip) ) { - found = true; - client = m_Clients[i]; - *index = i; + return *it++; } + it++; } - return client; + return NULL; } -CClient *CClients::FindNextClient(const CCallsign &Callsign, const CIp &Ip, int Protocol, int *index) +CClient *CClients::FindNextClient(const CCallsign &Callsign, const CIp &Ip, int Protocol, std::list::iterator &it) { - CClient *client = NULL; - - // find next client - bool found = false; - for ( int i = *index+1; (i < m_Clients.size()) && !found; i++ ) + while ( it != end() ) { - if ( (m_Clients[i]->GetProtocol() == Protocol) && - (m_Clients[i]->GetIp() == Ip) && - m_Clients[i]->GetCallsign().HasSameCallsign(Callsign) ) + if ( ((*it)->GetProtocol() == Protocol) && + ((*it)->GetIp() == Ip) && + (*it)->GetCallsign().HasSameCallsign(Callsign) ) { - found = true; - client = m_Clients[i]; - *index = i; + return *it++; } + it++; } - return client; + return NULL; } - diff --git a/src/cclients.h b/src/cclients.h index 8c5d010..8c7e3a3 100644 --- a/src/cclients.h +++ b/src/cclients.h @@ -4,6 +4,7 @@ // // Created by Jean-Luc Deltombe (LX3JL) on 31/10/2015. // Copyright © 2015 Jean-Luc Deltombe (LX3JL). All rights reserved. +// Copyright © 2020 Thomas A. Early, N7TAE // // ---------------------------------------------------------------------------- // This file is part of xlxd. @@ -19,7 +20,7 @@ // GNU General Public License for more details. // // You should have received a copy of the GNU General Public License -// along with Foobar. If not, see . +// along with Foobar. If not, see . // ---------------------------------------------------------------------------- #ifndef cclients_h @@ -40,21 +41,26 @@ class CClients public: // constructors CClients(); - + // destructors virtual ~CClients(); - + // locks void Lock(void) { m_Mutex.lock(); } void Unlock(void) { m_Mutex.unlock(); } - + // manage Clients int GetSize(void) const { return (int)m_Clients.size(); } void AddClient(CClient *); void RemoveClient(CClient *); - CClient *GetClient(int); bool IsClient(CClient *) const; - + + // pass-thru + std::list::iterator begin() { return m_Clients.begin(); } + std::list::iterator end() { return m_Clients.end(); } + std::list::const_iterator cbegin() const { return m_Clients.cbegin(); } + std::list::const_iterator cend() const { return m_Clients.cend(); } + // find clients CClient *FindClient(const CIp &); CClient *FindClient(const CIp &, int); @@ -62,16 +68,16 @@ public: CClient *FindClient(const CCallsign &, const CIp &, int); CClient *FindClient(const CCallsign &, char, const CIp &, int); CClient *FindClient(const CCallsign &, int); - + // iterate on clients - CClient *FindNextClient(int, int*); - CClient *FindNextClient(const CIp &, int, int *); - CClient *FindNextClient(const CCallsign &, const CIp &, int, int *); + CClient *FindNextClient(int, std::list::iterator &); + CClient *FindNextClient(const CIp &, int, std::list::iterator &); + CClient *FindNextClient(const CCallsign &, const CIp &, int, std::list::iterator &); protected: // data - std::mutex m_Mutex; - std::vector m_Clients; + std::mutex m_Mutex; + std::list m_Clients; }; diff --git a/src/cdcsprotocol.cpp b/src/cdcsprotocol.cpp index 27a0d79..f4f7b27 100644 --- a/src/cdcsprotocol.cpp +++ b/src/cdcsprotocol.cpp @@ -4,6 +4,7 @@ // // Created by Jean-Luc Deltombe (LX3JL) on 07/11/2015. // Copyright © 2015 Jean-Luc Deltombe (LX3JL). All rights reserved. +// Copyright © 2020 Thomas A. Early, N7TAE // // ---------------------------------------------------------------------------- // This file is part of xlxd. @@ -19,7 +20,7 @@ // GNU General Public License for more details. // // You should have received a copy of the GNU General Public License -// along with Foobar. If not, see . +// along with Foobar. If not, see . // ---------------------------------------------------------------------------- #include "main.h" @@ -35,23 +36,23 @@ bool CDcsProtocol::Init(void) { bool ok; - + // base class ok = CProtocol::Init(); - + // update the reflector callsign m_ReflectorCallsign.PatchCallsign(0, (const uint8 *)"DCS", 3); - + // create our socket ok &= m_Socket.Open(DCS_PORT); if ( !ok ) { std::cout << "Error opening socket on port UDP" << DCS_PORT << " on ip " << g_Reflector.GetListenIp() << std::endl; } - + // update time m_LastKeepaliveTime.Now(); - + // done return ok; } @@ -69,7 +70,7 @@ void CDcsProtocol::Task(void) char ToLinkModule; CDvHeaderPacket *Header; CDvFramePacket *Frame; - + // handle incoming packets if ( m_Socket.Receive(&Buffer, &Ip, 20) != -1 ) { @@ -77,13 +78,13 @@ void CDcsProtocol::Task(void) if ( IsValidDvPacket(Buffer, &Header, &Frame) ) { //std::cout << "DCS DV packet" << std::endl; - + // callsign muted? if ( g_GateKeeper.MayTransmit(Header->GetMyCallsign(), Ip, PROTOCOL_DCS, Header->GetRpt2Module()) ) { // handle it OnDvHeaderPacketIn(Header, Ip); - + if ( !Frame->IsLastPacket() ) { //std::cout << "DCS DV frame" << std::endl; @@ -104,7 +105,7 @@ void CDcsProtocol::Task(void) else if ( IsValidConnectPacket(Buffer, &Callsign, &ToLinkModule) ) { std::cout << "DCS connect packet for module " << ToLinkModule << " from " << Callsign << " at " << Ip << std::endl; - + // callsign authorized? if ( g_GateKeeper.MayLink(Callsign, Ip, PROTOCOL_DCS) && g_Reflector.IsValidModule(ToLinkModule) ) { @@ -114,10 +115,10 @@ void CDcsProtocol::Task(void) // acknowledge the request EncodeConnectAckPacket(Callsign, ToLinkModule, &Buffer); m_Socket.Send(Buffer, Ip); - + // create the client CDcsClient *client = new CDcsClient(Callsign, Ip, ToLinkModule); - + // and append g_Reflector.GetClients()->AddClient(client); g_Reflector.ReleaseClients(); @@ -125,7 +126,7 @@ void CDcsProtocol::Task(void) else { std::cout << "DCS node " << Callsign << " connect attempt on non-existing module" << std::endl; - + // deny the request EncodeConnectNackPacket(Callsign, ToLinkModule, &Buffer); m_Socket.Send(Buffer, Ip); @@ -137,12 +138,12 @@ void CDcsProtocol::Task(void) EncodeConnectNackPacket(Callsign, ToLinkModule, &Buffer); m_Socket.Send(Buffer, Ip); } - + } else if ( IsValidDisconnectPacket(Buffer, &Callsign) ) { std::cout << "DCS disconnect packet from " << Callsign << " at " << Ip << std::endl; - + // find client CClients *clients = g_Reflector.GetClients(); CClient *client = clients->FindClient(Ip, PROTOCOL_DCS); @@ -159,12 +160,12 @@ void CDcsProtocol::Task(void) else if ( IsValidKeepAlivePacket(Buffer, &Callsign) ) { //std::cout << "DCS keepalive packet from " << Callsign << " at " << Ip << std::endl; - + // find all clients with that callsign & ip and keep them alive CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(Callsign, Ip, PROTOCOL_DCS, &index)) != NULL ) + while ( (client = clients->FindNextClient(Callsign, Ip, PROTOCOL_DCS, it)) != NULL ) { client->Alive(); } @@ -181,19 +182,19 @@ void CDcsProtocol::Task(void) std::cout << "DCS packet (" << Buffer.size() << ") from " << Ip << std::endl; } } - + // handle end of streaming timeout CheckStreamsTimeout(); - + // handle queue from reflector HandleQueue(); - + // keep client alive if ( m_LastKeepaliveTime.DurationSinceNow() > DCS_KEEPALIVE_PERIOD ) { // HandleKeepalives(); - + // update time m_LastKeepaliveTime.Now(); } @@ -205,14 +206,14 @@ void CDcsProtocol::Task(void) bool CDcsProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) { bool newstream = false; - + // find the stream CPacketStream *stream = GetStream(Header->GetStreamId()); if ( stream == NULL ) { // no stream open yet, open a new one CCallsign via(Header->GetRpt1Callsign()); - + // find this client CClient *client = g_Reflector.GetClients()->FindClient(Ip, PROTOCOL_DCS); if ( client != NULL ) @@ -229,11 +230,11 @@ bool CDcsProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) } // release g_Reflector.ReleaseClients(); - + // update last heard g_Reflector.GetUsers()->Hearing(Header->GetMyCallsign(), via, Header->GetRpt2Callsign()); g_Reflector.ReleaseUsers(); - + // delete header if needed if ( !newstream ) { @@ -248,7 +249,7 @@ bool CDcsProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) // and delete packet delete Header; } - + // done return newstream; } @@ -264,10 +265,10 @@ void CDcsProtocol::HandleQueue(void) // get the packet CPacket *packet = m_Queue.front(); m_Queue.pop(); - + // get our sender's id int iModId = g_Reflector.GetModuleIndex(packet->GetModuleId()); - + // check if it's header and update cache if ( packet->IsDvHeader() ) { @@ -295,28 +296,28 @@ void CDcsProtocol::HandleQueue(void) m_StreamsCache[iModId].m_iSeqCounter++, &buffer); } - + // send it if ( buffer.size() > 0 ) { // and push it to all our clients linked to the module and who are not streaming in CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DCS, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DCS, it)) != NULL ) { // is this client busy ? if ( !client->IsAMaster() && (client->GetReflectorModule() == packet->GetModuleId()) ) { // no, send the packet m_Socket.Send(buffer, client->GetIp()); - + } } g_Reflector.ReleaseClients(); } } - + // done delete packet; } @@ -333,21 +334,21 @@ void CDcsProtocol::HandleKeepalives(void) // so, send keepalives to all CBuffer keepalive1; EncodeKeepAlivePacket(&keepalive1); - + // iterate on clients CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DCS, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DCS, it)) != NULL ) { // encode client's specific keepalive packet CBuffer keepalive2; EncodeKeepAlivePacket(&keepalive2, client); - + // send keepalive m_Socket.Send(keepalive1, client->GetIp()); m_Socket.Send(keepalive2, client->GetIp()); - + // is this client busy ? if ( client->IsAMaster() ) { @@ -361,12 +362,12 @@ void CDcsProtocol::HandleKeepalives(void) CBuffer disconnect; EncodeDisconnectPacket(&disconnect, client); m_Socket.Send(disconnect, client->GetIp()); - + // remove it std::cout << "DCS client " << client->GetCallsign() << " keepalive timeout" << std::endl; clients->RemoveClient(client); } - + } g_Reflector.ReleaseClients(); } @@ -419,17 +420,17 @@ bool CDcsProtocol::IsValidKeepAlivePacket(const CBuffer &Buffer, CCallsign *call bool CDcsProtocol::IsValidDvPacket(const CBuffer &Buffer, CDvHeaderPacket **header, CDvFramePacket **frame) { uint8 tag[] = { '0','0','0','1' }; - + bool valid = false; *header = NULL; *frame = NULL; - + if ( (Buffer.size() >= 100) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { // get the header *header = new CDvHeaderPacket((struct dstar_header *)&(Buffer.data()[4]), *((uint16 *)&(Buffer.data()[43])), 0x80); - + // get the frame if ( ((Buffer.data()[45]) & 0x40) != 0 ) { @@ -443,7 +444,7 @@ bool CDcsProtocol::IsValidDvPacket(const CBuffer &Buffer, CDvHeaderPacket **head *frame = new CDvFramePacket((struct dstar_dvframe *)&(Buffer.data()[46]), *((uint16 *)&(Buffer.data()[43])), Buffer.data()[45]); } - + // check validity of packets if ( !((*header)->IsValid() && (*frame)->IsValid()) ) { @@ -465,7 +466,7 @@ bool CDcsProtocol::IsIgnorePacket(const CBuffer &Buffer) { bool valid = false; uint8 tag[] = { 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, }; - + if ( Buffer.size() == 15 ) { valid = (Buffer.Compare(tag, sizeof(tag)) == 0); @@ -485,7 +486,7 @@ void CDcsProtocol::EncodeKeepAlivePacket(CBuffer *Buffer) void CDcsProtocol::EncodeKeepAlivePacket(CBuffer *Buffer, CClient *Client) { uint8 tag[] = { 0x0A,0x00,0x20,0x20 }; - + Buffer->Set((uint8 *)(const char *)GetReflectorCallsign(), CALLSIGN_LEN-1); Buffer->Append((uint8)Client->GetReflectorModule()); Buffer->Append((uint8)' '); @@ -499,7 +500,7 @@ void CDcsProtocol::EncodeConnectAckPacket(const CCallsign &Callsign, char Reflec { uint8 tag[] = { 'A','C','K',0x00 }; uint8 cs[CALLSIGN_LEN]; - + Callsign.GetCallsign(cs); Buffer->Set(cs, CALLSIGN_LEN-1); Buffer->Append((uint8)' '); @@ -512,7 +513,7 @@ void CDcsProtocol::EncodeConnectNackPacket(const CCallsign &Callsign, char Refle { uint8 tag[] = { 'N','A','K',0x00 }; uint8 cs[CALLSIGN_LEN]; - + Callsign.GetCallsign(cs); Buffer->Set(cs, CALLSIGN_LEN-1); Buffer->Append((uint8)' '); diff --git a/src/cdextraprotocol.cpp b/src/cdextraprotocol.cpp index 8e5866a..9f96f28 100644 --- a/src/cdextraprotocol.cpp +++ b/src/cdextraprotocol.cpp @@ -200,9 +200,9 @@ void CDextraProtocol::Task(void) // find all clients with that callsign & ip and keep them alive CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(Callsign, Ip, PROTOCOL_DEXTRA, &index)) != NULL ) + while ( (client = clients->FindNextClient(Callsign, Ip, PROTOCOL_DEXTRA, it)) != NULL ) { client->Alive(); } @@ -260,9 +260,9 @@ void CDextraProtocol::HandleQueue(void) { // and push it to all our clients linked to the module and who are not streaming in CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DEXTRA, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DEXTRA, it)) != NULL ) { // is this client busy ? if ( !client->IsAMaster() && (client->GetReflectorModule() == packet->GetModuleId()) ) @@ -298,9 +298,9 @@ void CDextraProtocol::HandleKeepalives(void) // iterate on clients CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DEXTRA, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DEXTRA, it)) != NULL ) { // send keepalive m_Socket.Send(keepalive, client->GetIp()); @@ -339,7 +339,7 @@ void CDextraProtocol::HandleKeepalives(void) // iterate on peers CPeers *peers = g_Reflector.GetPeers(); - index = -1; + int index = -1; CPeer *peer = NULL; while ( (peer = peers->FindNextPeer(PROTOCOL_DEXTRA, &index)) != NULL ) { diff --git a/src/cdmrmmdvmprotocol.cpp b/src/cdmrmmdvmprotocol.cpp index 2398fd1..24d0aa8 100644 --- a/src/cdmrmmdvmprotocol.cpp +++ b/src/cdmrmmdvmprotocol.cpp @@ -56,24 +56,24 @@ static uint8 g_DmrSyncMSData[] = { 0x0D,0x5D,0x7F,0x77,0xFD,0x75,0x70 }; bool CDmrmmdvmProtocol::Init(void) { bool ok; - + // base class ok = CProtocol::Init(); - + // update the reflector callsign //m_ReflectorCallsign.PatchCallsign(0, (const uint8 *)"DMR", 3); - + // create our socket ok &= m_Socket.Open(DMRMMDVM_PORT); - + // update time m_LastKeepaliveTime.Now(); - + // random number generator time_t t; ::srand((unsigned) time(&t)); m_uiAuthSeed = (uint32)rand(); - + // done return ok; } @@ -94,7 +94,7 @@ void CDmrmmdvmProtocol::Task(void) CDvHeaderPacket *Header; CDvFramePacket *Frames[3]; CDvLastFramePacket *LastFrame; - + // handle incoming packets if ( m_Socket.Receive(&Buffer, &Ip, 20) != -1 ) { @@ -103,7 +103,7 @@ void CDmrmmdvmProtocol::Task(void) if ( IsValidDvFramePacket(Buffer, Frames) ) { //std::cout << "DMRmmdvm DV frame" << std::endl; - + for ( int i = 0; i < 3; i++ ) { OnDvFramePacketIn(Frames[i], &Ip); @@ -113,7 +113,7 @@ void CDmrmmdvmProtocol::Task(void) { //std::cout << "DMRmmdvm DV header:" << std::endl << *Header << std::endl; //std::cout << "DMRmmdvm DV header" << std::endl; - + // callsign muted? if ( g_GateKeeper.MayTransmit(Header->GetMyCallsign(), Ip, PROTOCOL_DMRMMDVM) ) { @@ -128,13 +128,13 @@ void CDmrmmdvmProtocol::Task(void) else if ( IsValidDvLastFramePacket(Buffer, &LastFrame) ) { //std::cout << "DMRmmdvm DV last frame" << std::endl; - + OnDvLastFramePacketIn(LastFrame, &Ip); } else if ( IsValidConnectPacket(Buffer, &Callsign, Ip) ) { std::cout << "DMRmmdvm connect packet from " << Callsign << " at " << Ip << std::endl; - + // callsign authorized? if ( g_GateKeeper.MayLink(Callsign, Ip, PROTOCOL_DMRMMDVM) ) { @@ -148,19 +148,19 @@ void CDmrmmdvmProtocol::Task(void) EncodeNackPacket(&Buffer, Callsign); m_Socket.Send(Buffer, Ip); } - + } else if ( IsValidAuthenticationPacket(Buffer, &Callsign, Ip) ) { std::cout << "DMRmmdvm authentication packet from " << Callsign << " at " << Ip << std::endl; - + // callsign authorized? if ( g_GateKeeper.MayLink(Callsign, Ip, PROTOCOL_DMRMMDVM) ) { // acknowledge the request EncodeAckPacket(&Buffer, Callsign); m_Socket.Send(Buffer, Ip); - + // add client if needed CClients *clients = g_Reflector.GetClients(); CClient *client = clients->FindClient(Callsign, Ip, PROTOCOL_DMRMMDVM); @@ -168,10 +168,10 @@ void CDmrmmdvmProtocol::Task(void) if ( client == NULL ) { std::cout << "DMRmmdvm login from " << Callsign << " at " << Ip << std::endl; - + // create the client CDmrmmdvmClient *newclient = new CDmrmmdvmClient(Callsign, Ip); - + // and append clients->AddClient(newclient); } @@ -188,12 +188,12 @@ void CDmrmmdvmProtocol::Task(void) EncodeNackPacket(&Buffer, Callsign); m_Socket.Send(Buffer, Ip); } - + } else if ( IsValidDisconnectPacket(Buffer, &Callsign) ) { std::cout << "DMRmmdvm disconnect packet from " << Callsign << " at " << Ip << std::endl; - + // find client & remove it CClients *clients = g_Reflector.GetClients(); CClient *client = clients->FindClient(Ip, PROTOCOL_DMRMMDVM); @@ -206,7 +206,7 @@ void CDmrmmdvmProtocol::Task(void) else if ( IsValidConfigPacket(Buffer, &Callsign, Ip) ) { std::cout << "DMRmmdvm configuration packet from " << Callsign << " at " << Ip << std::endl; - + // acknowledge the request EncodeAckPacket(&Buffer, Callsign); m_Socket.Send(Buffer, Ip); @@ -214,17 +214,17 @@ void CDmrmmdvmProtocol::Task(void) else if ( IsValidKeepAlivePacket(Buffer, &Callsign) ) { //std::cout << "DMRmmdvm keepalive packet from " << Callsign << " at " << Ip << std::endl; - + // find all clients with that callsign & ip and keep them alive CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(Callsign, Ip, PROTOCOL_DMRMMDVM, &index)) != NULL ) + while ( (client = clients->FindNextClient(Callsign, Ip, PROTOCOL_DMRMMDVM, it)) != NULL ) { // acknowledge EncodeKeepAlivePacket(&Buffer, client); m_Socket.Send(Buffer, Ip); - + // and mark as alive client->Alive(); } @@ -233,13 +233,13 @@ void CDmrmmdvmProtocol::Task(void) else if ( IsValidRssiPacket(Buffer, &Callsign, &iRssi) ) { // std::cout << "DMRmmdvm RSSI packet from " << Callsign << " at " << Ip << std::endl - + // ignore... } else if ( IsValidOptionPacket(Buffer, &Callsign) ) { std::cout << "DMRmmdvm options packet from " << Callsign << " at " << Ip << std::endl; - + // acknowledge the request EncodeAckPacket(&Buffer, Callsign); m_Socket.Send(Buffer, Ip); @@ -250,24 +250,24 @@ void CDmrmmdvmProtocol::Task(void) //std::cout << Buffer << std::endl; } } - + // handle end of streaming timeout CheckStreamsTimeout(); - + // handle queue from reflector HandleQueue(); - - + + // keep client alive if ( m_LastKeepaliveTime.DurationSinceNow() > DMRMMDVM_KEEPALIVE_PERIOD ) { // HandleKeepalives(); - + // update time m_LastKeepaliveTime.Now(); } - + } //////////////////////////////////////////////////////////////////////////////////////// @@ -277,7 +277,7 @@ bool CDmrmmdvmProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &I { bool newstream = false; bool lastheard = false; - + // CCallsign via(Header->GetRpt1Callsign()); @@ -323,7 +323,7 @@ bool CDmrmmdvmProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &I Header->SetRpt2Module(client->GetReflectorModule()); } } - + // and now, re-check module is valid && that it's not a private call if ( g_Reflector.IsValidModule(Header->GetRpt2Module()) && (CallType == DMR_GROUP_CALL) ) { @@ -341,17 +341,17 @@ bool CDmrmmdvmProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &I { lastheard = true; } - + // release g_Reflector.ReleaseClients(); - + // update last heard if ( lastheard ) { g_Reflector.GetUsers()->Hearing(Header->GetMyCallsign(), via, Header->GetRpt2Callsign()); g_Reflector.ReleaseUsers(); } - + // delete header if needed if ( !newstream ) { @@ -366,7 +366,7 @@ bool CDmrmmdvmProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &I // and delete packet delete Header; } - + // done return newstream; } @@ -376,20 +376,20 @@ bool CDmrmmdvmProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &I void CDmrmmdvmProtocol::HandleQueue(void) { - + m_Queue.Lock(); while ( !m_Queue.empty() ) { // get the packet CPacket *packet = m_Queue.front(); m_Queue.pop(); - + // get our sender's id int iModId = g_Reflector.GetModuleIndex(packet->GetModuleId()); - + // encode CBuffer buffer; - + // check if it's header if ( packet->IsDvHeader() ) { @@ -397,7 +397,7 @@ void CDmrmmdvmProtocol::HandleQueue(void) // this relies on queue feeder setting valid module id m_StreamsCache[iModId].m_dvHeader = CDvHeaderPacket((const CDvHeaderPacket &)*packet); m_StreamsCache[iModId].m_uiSeqId = 0; - + // encode it EncodeDvHeaderPacket((const CDvHeaderPacket &)*packet, m_StreamsCache[iModId].m_uiSeqId, &buffer); m_StreamsCache[iModId].m_uiSeqId = 1; @@ -435,27 +435,27 @@ void CDmrmmdvmProtocol::HandleQueue(void) break; } } - + // send it if ( buffer.size() > 0 ) { // and push it to all our clients linked to the module and who are not streaming in CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DMRMMDVM, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DMRMMDVM, it)) != NULL ) { // is this client busy ? if ( !client->IsAMaster() && (client->GetReflectorModule() == packet->GetModuleId()) ) { // no, send the packet m_Socket.Send(buffer, client->GetIp()); - + } } g_Reflector.ReleaseClients(); } - + // done delete packet; } @@ -470,12 +470,12 @@ void CDmrmmdvmProtocol::HandleKeepalives(void) // DMRhomebrew protocol keepalive request is client tasks // here, just check that all clients are still alive // and disconnect them if not - + // iterate on clients CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DMRMMDVM, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DMRMMDVM, it)) != NULL ) { // is this client busy ? if ( client->IsAMaster() ) @@ -489,12 +489,12 @@ void CDmrmmdvmProtocol::HandleKeepalives(void) // no, disconnect CBuffer disconnect; m_Socket.Send(disconnect, client->GetIp()); - + // remove it std::cout << "DMRmmdvm client " << client->GetCallsign() << " keepalive timeout" << std::endl; clients->RemoveClient(client); } - + } g_Reflector.ReleaseClients(); } @@ -505,7 +505,7 @@ void CDmrmmdvmProtocol::HandleKeepalives(void) bool CDmrmmdvmProtocol::IsValidKeepAlivePacket(const CBuffer &Buffer, CCallsign *callsign) { uint8 tag[] = { 'R','P','T','P','I','N','G' }; - + bool valid = false; if ( (Buffer.size() == 11) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { @@ -520,7 +520,7 @@ bool CDmrmmdvmProtocol::IsValidKeepAlivePacket(const CBuffer &Buffer, CCallsign bool CDmrmmdvmProtocol::IsValidConnectPacket(const CBuffer &Buffer, CCallsign *callsign, const CIp &Ip) { uint8 tag[] = { 'R','P','T','L' }; - + bool valid = false; if ( (Buffer.size() == 8) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { @@ -539,7 +539,7 @@ bool CDmrmmdvmProtocol::IsValidConnectPacket(const CBuffer &Buffer, CCallsign *c bool CDmrmmdvmProtocol::IsValidAuthenticationPacket(const CBuffer &Buffer, CCallsign *callsign, const CIp &Ip) { uint8 tag[] = { 'R','P','T','K' }; - + bool valid = false; if ( (Buffer.size() == 40) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { @@ -559,7 +559,7 @@ bool CDmrmmdvmProtocol::IsValidAuthenticationPacket(const CBuffer &Buffer, CCall bool CDmrmmdvmProtocol::IsValidDisconnectPacket(const CBuffer &Buffer, CCallsign *callsign) { uint8 tag[] = { 'R','P','T','C','L' }; - + bool valid = false; if ( (Buffer.size() == 13) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { @@ -574,7 +574,7 @@ bool CDmrmmdvmProtocol::IsValidDisconnectPacket(const CBuffer &Buffer, CCallsign bool CDmrmmdvmProtocol::IsValidConfigPacket(const CBuffer &Buffer, CCallsign *callsign, const CIp &Ip) { uint8 tag[] = { 'R','P','T','C' }; - + bool valid = false; if ( (Buffer.size() == 302) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { @@ -594,7 +594,7 @@ bool CDmrmmdvmProtocol::IsValidConfigPacket(const CBuffer &Buffer, CCallsign *ca bool CDmrmmdvmProtocol::IsValidOptionPacket(const CBuffer &Buffer, CCallsign *callsign) { uint8 tag[] = { 'R','P','T','O' }; - + bool valid = false; if ( (Buffer.size() >= 8) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { @@ -609,7 +609,7 @@ bool CDmrmmdvmProtocol::IsValidOptionPacket(const CBuffer &Buffer, CCallsign *ca bool CDmrmmdvmProtocol::IsValidRssiPacket(const CBuffer &Buffer, CCallsign *callsign, int *rssi) { uint8 tag[] = { 'R','P','T','I','N','T','R' }; - + bool valid = false; if ( (Buffer.size() == 17) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { @@ -624,11 +624,11 @@ bool CDmrmmdvmProtocol::IsValidRssiPacket(const CBuffer &Buffer, CCallsign *call bool CDmrmmdvmProtocol::IsValidDvHeaderPacket(const CBuffer &Buffer, CDvHeaderPacket **header, uint8 *cmd, uint8 *CallType) { uint8 tag[] = { 'D','M','R','D' }; - + bool valid = false; *header = NULL; *cmd = CMD_NONE; - + if ( (Buffer.size() == 55) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { // frame details @@ -654,7 +654,7 @@ bool CDmrmmdvmProtocol::IsValidDvHeaderPacket(const CBuffer &Buffer, CDvHeaderPa //CBPTC19696 bptc; //uint8 lcdata[12]; //bptc.decode(&(Buffer.data()[20]), lcdata); - + // crack DMR header //uint8 uiSeqId = Buffer.data()[4]; uint32 uiSrcId = MAKEDWORD(MAKEWORD(Buffer.data()[7],Buffer.data()[6]),MAKEWORD(Buffer.data()[5],0)); @@ -662,10 +662,10 @@ bool CDmrmmdvmProtocol::IsValidDvHeaderPacket(const CBuffer &Buffer, CDvHeaderPa uint32 uiRptrId = MAKEDWORD(MAKEWORD(Buffer.data()[14],Buffer.data()[13]),MAKEWORD(Buffer.data()[12],Buffer.data()[11])); //uint8 uiVoiceSeq = (Buffer.data()[15] & 0x0F); uint32 uiStreamId = *(uint32 *)(&Buffer.data()[16]); - + // call type *CallType = uiCallType; - + // link/unlink command ? if ( uiDstId == 4000 ) { @@ -679,14 +679,14 @@ bool CDmrmmdvmProtocol::IsValidDvHeaderPacket(const CBuffer &Buffer, CDvHeaderPa { *cmd = CMD_NONE; } - + // build DVHeader CCallsign csMY = CCallsign("", uiSrcId); CCallsign rpt1 = CCallsign("", uiRptrId); rpt1.SetModule(MMDVM_MODULE_ID); CCallsign rpt2 = m_ReflectorCallsign; rpt2.SetModule(DmrDstIdToModule(uiDstId)); - + // and packet *header = new CDvHeaderPacket(uiSrcId, CCallsign("CQCQCQ"), rpt1, rpt2, uiStreamId, 0, 0); valid = (*header)->IsValid(); @@ -705,12 +705,12 @@ bool CDmrmmdvmProtocol::IsValidDvHeaderPacket(const CBuffer &Buffer, CDvHeaderPa bool CDmrmmdvmProtocol::IsValidDvFramePacket(const CBuffer &Buffer, CDvFramePacket **frames) { uint8 tag[] = { 'D','M','R','D' }; - + bool valid = false; frames[0] = NULL; frames[1] = NULL; frames[2] = NULL; - + if ( (Buffer.size() == 55) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { // frame details @@ -727,7 +727,7 @@ bool CDmrmmdvmProtocol::IsValidDvFramePacket(const CBuffer &Buffer, CDvFramePack //uint32 uiRptrId = MAKEDWORD(MAKEWORD(Buffer.data()[14],Buffer.data()[13]),MAKEWORD(Buffer.data()[12],Buffer.data()[11])); uint8 uiVoiceSeq = (Buffer.data()[15] & 0x0F); uint32 uiStreamId = *(uint32 *)(&Buffer.data()[16]); - + // crack payload uint8 dmrframe[33]; uint8 dmr3ambe[27]; @@ -744,25 +744,25 @@ bool CDmrmmdvmProtocol::IsValidDvFramePacket(const CBuffer &Buffer, CDvFramePack dmrsync[0] = dmrframe[13] & 0x0F; ::memcpy(&dmrsync[1], &dmrframe[14], 5); dmrsync[6] = dmrframe[19] & 0xF0; - + // debug //CBuffer dump; //dump.Set(dmrsync, 6); //dump.DebugDump(g_Reflector.m_DebugFile); - + // and create 3 dv frames // frame1 memcpy(dmrambe, &dmr3ambe[0], 9); frames[0] = new CDvFramePacket(dmrambe, dmrsync, uiStreamId, uiVoiceSeq, 1); - + // frame2 memcpy(dmrambe, &dmr3ambe[9], 9); frames[1] = new CDvFramePacket(dmrambe, dmrsync, uiStreamId, uiVoiceSeq, 2); - + // frame3 memcpy(dmrambe, &dmr3ambe[18], 9); frames[2] = new CDvFramePacket(dmrambe, dmrsync, uiStreamId, uiVoiceSeq, 3); - + // check valid = true; } @@ -774,10 +774,10 @@ bool CDmrmmdvmProtocol::IsValidDvFramePacket(const CBuffer &Buffer, CDvFramePack bool CDmrmmdvmProtocol::IsValidDvLastFramePacket(const CBuffer &Buffer, CDvLastFramePacket **frame) { uint8 tag[] = { 'D','M','R','D' }; - + bool valid = false; *frame = NULL; - + if ( (Buffer.size() == 55) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { // frame details @@ -803,7 +803,7 @@ bool CDmrmmdvmProtocol::IsValidDvLastFramePacket(const CBuffer &Buffer, CDvLastF //CBPTC19696 bptc; //uint8 lcdata[12]; //bptc.decode(&(Buffer.data()[20]), lcdata); - + // crack DMR header //uint8 uiSeqId = Buffer.data()[4]; //uint32 uiSrcId = MAKEDWORD(MAKEWORD(Buffer.data()[7],Buffer.data()[6]),MAKEWORD(Buffer.data()[5],0)); @@ -811,15 +811,15 @@ bool CDmrmmdvmProtocol::IsValidDvLastFramePacket(const CBuffer &Buffer, CDvLastF //uint32 uiRptrId = MAKEDWORD(MAKEWORD(Buffer.data()[14],Buffer.data()[13]),MAKEWORD(Buffer.data()[12],Buffer.data()[11])); //uint8 uiVoiceSeq = (Buffer.data()[15] & 0x0F); uint32 uiStreamId = *(uint32 *)(&Buffer.data()[16]); - + // dummy ambe uint8 ambe[9]; ::memset(ambe, 0, sizeof(ambe)); - - + + // and packet *frame = new CDvLastFramePacket(ambe, dmrsync, uiStreamId, 0, 0); - + // check valid = true; } @@ -835,7 +835,7 @@ bool CDmrmmdvmProtocol::IsValidDvLastFramePacket(const CBuffer &Buffer, CDvLastF void CDmrmmdvmProtocol::EncodeKeepAlivePacket(CBuffer *Buffer, CClient *Client) { uint8 tag[] = { 'M','S','T','P','O','N','G' }; - + Buffer->Set(tag, sizeof(tag)); uint32 uiDmrId = Client->GetCallsign().GetDmrid(); Buffer->Append((uint8 *)&uiDmrId, 4); @@ -844,14 +844,14 @@ void CDmrmmdvmProtocol::EncodeKeepAlivePacket(CBuffer *Buffer, CClient *Client) void CDmrmmdvmProtocol::EncodeAckPacket(CBuffer *Buffer, const CCallsign &Callsign) { uint8 tag[] = { 'R','P','T','A','C','K' }; - + Buffer->Set(tag, sizeof(tag)); } void CDmrmmdvmProtocol::EncodeConnectAckPacket(CBuffer *Buffer, const CCallsign &Callsign, uint32 AuthSeed) { uint8 tag[] = { 'R','P','T','A','C','K' }; - + Buffer->Set(tag, sizeof(tag)); Buffer->Append(AuthSeed); } @@ -859,14 +859,14 @@ void CDmrmmdvmProtocol::EncodeConnectAckPacket(CBuffer *Buffer, const CCallsign void CDmrmmdvmProtocol::EncodeNackPacket(CBuffer *Buffer, const CCallsign &Callsign) { uint8 tag[] = { 'M','S','T','N','A','K' }; - + Buffer->Set(tag, sizeof(tag)); } void CDmrmmdvmProtocol::EncodeClosePacket(CBuffer *Buffer, CClient *Client) { uint8 tag[] = { 'M','S','T','C','L' }; - + Buffer->Set(tag, sizeof(tag)); } @@ -874,9 +874,9 @@ void CDmrmmdvmProtocol::EncodeClosePacket(CBuffer *Buffer, CClient *Client) bool CDmrmmdvmProtocol::EncodeDvHeaderPacket(const CDvHeaderPacket &Packet, uint8 seqid, CBuffer *Buffer) const { uint8 tag[] = { 'D','M','R','D' }; - + Buffer->Set(tag, sizeof(tag)); - + // DMR header // uiSeqId Buffer->Append((uint8)seqid); @@ -898,16 +898,16 @@ bool CDmrmmdvmProtocol::EncodeDvHeaderPacket(const CDvHeaderPacket &Packet, uint // uiStreamId uint32 uiStreamId = Packet.GetStreamId(); Buffer->Append((uint32)uiStreamId); - + // Payload AppendVoiceLCToBuffer(Buffer, uiSrcId); - + // BER Buffer->Append((uint8)0); - + // RSSI Buffer->Append((uint8)0); - + // done return true; } @@ -919,7 +919,7 @@ void CDmrmmdvmProtocol::EncodeDvPacket( { uint8 tag[] = { 'D','M','R','D' }; Buffer->Set(tag, sizeof(tag)); - + // DMR header // uiSeqId Buffer->Append((uint8)seqid); @@ -945,11 +945,11 @@ void CDmrmmdvmProtocol::EncodeDvPacket( } uiBitField |= (DvFrame0.GetDmrPacketId() & 0x0F); Buffer->Append((uint8)uiBitField); - + // uiStreamId uint32 uiStreamId = Header.GetStreamId(); Buffer->Append((uint32)uiStreamId); - + // Payload // frame0 Buffer->ReplaceAt(20, DvFrame0.GetAmbePlus(), 9); @@ -961,7 +961,7 @@ void CDmrmmdvmProtocol::EncodeDvPacket( Buffer->ReplaceAt(39, (uint8)(Buffer->at(39) & 0x0F)); // frame2 Buffer->ReplaceAt(44, DvFrame2.GetAmbePlus(), 9); - + // sync or embedded signaling ReplaceEMBInBuffer(Buffer, DvFrame0.GetDmrPacketId()); @@ -972,18 +972,18 @@ void CDmrmmdvmProtocol::EncodeDvPacket( // BER Buffer->Append((uint8)0); - + // RSSI - Buffer->Append((uint8)0); + Buffer->Append((uint8)0); } void CDmrmmdvmProtocol::EncodeDvLastPacket(const CDvHeaderPacket &Packet, uint8 seqid, CBuffer *Buffer) const { uint8 tag[] = { 'D','M','R','D' }; - + Buffer->Set(tag, sizeof(tag)); - + // DMR header // uiSeqId Buffer->Append((uint8)seqid); @@ -1005,13 +1005,13 @@ void CDmrmmdvmProtocol::EncodeDvLastPacket(const CDvHeaderPacket &Packet, uint8 // uiStreamId uint32 uiStreamId = Packet.GetStreamId(); Buffer->Append((uint32)uiStreamId); - + // Payload AppendTerminatorLCToBuffer(Buffer, uiSrcId); - + // BER Buffer->Append((uint8)0); - + // RSSI Buffer->Append((uint8)0); } @@ -1041,7 +1041,7 @@ uint32 CDmrmmdvmProtocol::ModuleToDmrDestId(char m) const void CDmrmmdvmProtocol::AppendVoiceLCToBuffer(CBuffer *buffer, uint32 uiSrcId) const { uint8 payload[33]; - + // fill payload CBPTC19696 bptc; ::memset(payload, 0, sizeof(payload)); @@ -1076,11 +1076,11 @@ void CDmrmmdvmProtocol::AppendVoiceLCToBuffer(CBuffer *buffer, uint32 uiSrcId) c payload[13U] = (payload[13U] & 0x0FU) | ((slottype[0U] << 6) & 0xC0U) | ((slottype[1U] >> 2) & 0x30U); payload[19U] = (payload[19U] & 0xF0U) | ((slottype[1U] >> 2) & 0x0FU); payload[20U] = (payload[20U] & 0x03U) | ((slottype[1U] << 6) & 0xC0U) | ((slottype[2U] >> 2) & 0x3CU); - + } // and encode bptc.encode(lc, payload); - + // and append buffer->Append(payload, sizeof(payload)); } @@ -1088,7 +1088,7 @@ void CDmrmmdvmProtocol::AppendVoiceLCToBuffer(CBuffer *buffer, uint32 uiSrcId) c void CDmrmmdvmProtocol::AppendTerminatorLCToBuffer(CBuffer *buffer, uint32 uiSrcId) const { uint8 payload[33]; - + // fill payload CBPTC19696 bptc; ::memset(payload, 0, sizeof(payload)); @@ -1126,7 +1126,7 @@ void CDmrmmdvmProtocol::AppendTerminatorLCToBuffer(CBuffer *buffer, uint32 uiSrc } // and encode bptc.encode(lc, payload); - + // and append buffer->Append(payload, sizeof(payload)); } diff --git a/src/cdmrplusprotocol.cpp b/src/cdmrplusprotocol.cpp index 1d1180f..cb9b19f 100644 --- a/src/cdmrplusprotocol.cpp +++ b/src/cdmrplusprotocol.cpp @@ -4,6 +4,7 @@ // // Created by Jean-Luc Deltombe (LX3JL) on 10/01/2016. // Copyright © 2015 Jean-Luc Deltombe (LX3JL). All rights reserved. +// Copyright © 2020 Thomas A. Early, N7TAE // // ---------------------------------------------------------------------------- // This file is part of xlxd. @@ -49,23 +50,23 @@ static uint8 g_DmrSyncMSData[] = { 0x0D,0x5D,0x7F,0x77,0xFD,0x75,0x70 }; bool CDmrplusProtocol::Init(void) { bool ok; - + // base class ok = CProtocol::Init(); - + // update the reflector callsign //m_ReflectorCallsign.PatchCallsign(0, (const uint8 *)"DMR", 3); - + // create our socket ok &= m_Socket.Open(DMRPLUS_PORT); - + // update time m_LastKeepaliveTime.Now(); - + // random number generator time_t t; ::srand((unsigned) time(&t)); - + // done return ok; } @@ -83,7 +84,7 @@ void CDmrplusProtocol::Task(void) char ToLinkModule; CDvHeaderPacket *Header; CDvFramePacket *Frames[3]; - + // handle incoming packets if ( m_Socket.Receive(&Buffer, &Ip, 20) != -1 ) { @@ -113,7 +114,7 @@ void CDmrplusProtocol::Task(void) //std::cout << "DMRplus DV header:" << std::endl; //std::cout << "DMRplus DV header:" << std::endl << *Header << std::endl; //Buffer.DebugDump(g_Reflector.m_DebugFile); - + // callsign muted? if ( g_GateKeeper.MayTransmit(Header->GetMyCallsign(), Ip, PROTOCOL_DMRPLUS) ) { @@ -128,14 +129,14 @@ void CDmrplusProtocol::Task(void) else if ( IsValidConnectPacket(Buffer, &Callsign, &ToLinkModule, Ip) ) { //std::cout << "DMRplus keepalive/connect packet for module " << ToLinkModule << " from " << Callsign << " at " << Ip << std::endl; - + // callsign authorized? if ( g_GateKeeper.MayLink(Callsign, Ip, PROTOCOL_DMRPLUS) ) { // acknowledge the request EncodeConnectAckPacket(&Buffer); m_Socket.Send(Buffer, Ip); - + // add client if needed CClients *clients = g_Reflector.GetClients(); CClient *client = clients->FindClient(Callsign, Ip, PROTOCOL_DMRPLUS); @@ -143,10 +144,10 @@ void CDmrplusProtocol::Task(void) if ( client == NULL ) { std::cout << "DMRplus connect packet for module " << ToLinkModule << " from " << Callsign << " at " << Ip << std::endl; - + // create the client CDmrplusClient *newclient = new CDmrplusClient(Callsign, Ip, ToLinkModule); - + // and append clients->AddClient(newclient); } @@ -163,12 +164,12 @@ void CDmrplusProtocol::Task(void) EncodeConnectNackPacket(&Buffer); m_Socket.Send(Buffer, Ip); } - + } else if ( IsValidDisconnectPacket(Buffer, &Callsign, &ToLinkModule) ) { std::cout << "DMRplus disconnect packet for module " << ToLinkModule << " from " << Callsign << " at " << Ip << std::endl; - + // find client & remove it CClients *clients = g_Reflector.GetClients(); CClient *client = clients->FindClient(Ip, PROTOCOL_DMRPLUS); @@ -183,20 +184,20 @@ void CDmrplusProtocol::Task(void) //std::cout << "DMRPlus packet (" << Buffer.size() << ")" << " at " << Ip << std::endl; } } - + // handle end of streaming timeout CheckStreamsTimeout(); - + // handle queue from reflector HandleQueue(); - - + + // keep client alive if ( m_LastKeepaliveTime.DurationSinceNow() > DMRPLUS_KEEPALIVE_PERIOD ) { // HandleKeepalives(); - + // update time m_LastKeepaliveTime.Now(); } @@ -208,7 +209,7 @@ void CDmrplusProtocol::Task(void) bool CDmrplusProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) { bool newstream = false; - + // find the stream CPacketStream *stream = GetStream(Header->GetStreamId()); if ( stream == NULL ) @@ -237,18 +238,18 @@ bool CDmrplusProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip // and delete packet delete Header; } - + // update last heard g_Reflector.GetUsers()->Hearing(Header->GetMyCallsign(), Header->GetRpt1Callsign(), Header->GetRpt2Callsign()); g_Reflector.ReleaseUsers(); - + // delete header if needed if ( !newstream ) { delete Header; } - - + + // done return newstream; } @@ -258,17 +259,17 @@ bool CDmrplusProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip void CDmrplusProtocol::HandleQueue(void) { - + m_Queue.Lock(); while ( !m_Queue.empty() ) { // get the packet CPacket *packet = m_Queue.front(); m_Queue.pop(); - + // get our sender's id int iModId = g_Reflector.GetModuleIndex(packet->GetModuleId()); - + // encode CBuffer buffer; @@ -279,7 +280,7 @@ void CDmrplusProtocol::HandleQueue(void) // this relies on queue feeder setting valid module id m_StreamsCache[iModId].m_dvHeader = CDvHeaderPacket((const CDvHeaderPacket &)*packet); m_StreamsCache[iModId].m_uiSeqId = 4; - + // encode it EncodeDvHeaderPacket((const CDvHeaderPacket &)*packet, &buffer); } @@ -307,17 +308,17 @@ void CDmrplusProtocol::HandleQueue(void) default: break; } - + } - + // send it if ( buffer.size() > 0 ) { // and push it to all our clients linked to the module and who are not streaming in CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DMRPLUS, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DMRPLUS, it)) != NULL ) { // is this client busy ? if ( !client->IsAMaster() && (client->GetReflectorModule() == packet->GetModuleId()) ) @@ -327,7 +328,7 @@ void CDmrplusProtocol::HandleQueue(void) } } g_Reflector.ReleaseClients(); - + // debug //buffer.DebugDump(g_Reflector.m_DebugFile); } @@ -344,9 +345,9 @@ void CDmrplusProtocol::SendBufferToClients(const CBuffer &buffer, uint8 module) { // and push it to all our clients linked to the module and who are not streaming in CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DMRPLUS, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DMRPLUS, it)) != NULL ) { // is this client busy ? if ( !client->IsAMaster() && (client->GetReflectorModule() == module) ) @@ -356,7 +357,7 @@ void CDmrplusProtocol::SendBufferToClients(const CBuffer &buffer, uint8 module) } } g_Reflector.ReleaseClients(); - + // debug //buffer.DebugDump(g_Reflector.m_DebugFile); } @@ -371,12 +372,12 @@ void CDmrplusProtocol::HandleKeepalives(void) // DMRplus protocol keepalive request is client tasks // here, just check that all clients are still alive // and disconnect them if not - + // iterate on clients CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DMRPLUS, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DMRPLUS, it)) != NULL ) { // is this client busy ? if ( client->IsAMaster() ) @@ -391,12 +392,12 @@ void CDmrplusProtocol::HandleKeepalives(void) //CBuffer disconnect; //EncodeDisconnectPacket(&disconnect, client); //m_Socket.Send(disconnect, client->GetIp()); - + // remove it std::cout << "DMRplus client " << client->GetCallsign() << " keepalive timeout" << std::endl; clients->RemoveClient(client); } - + } g_Reflector.ReleaseClients(); } @@ -471,7 +472,7 @@ bool CDmrplusProtocol::IsValidDvHeaderPacket(const CIp &Ip, const CBuffer &Buffe CCallsign rpt2 = m_ReflectorCallsign; rpt2.SetModule(DmrDstIdToModule(uiDstId)); uint32 uiStreamId = IpToStreamId(Ip); - + // and packet *Header = new CDvHeaderPacket(uiSrcId, CCallsign("CQCQCQ"), rpt1, rpt2, uiStreamId, 0, 0); valid = (*Header)->IsValid(); @@ -492,7 +493,7 @@ bool CDmrplusProtocol::IsValidDvFramePacket(const CIp &Ip, const CBuffer &Buffer frames[0] = NULL; frames[1] = NULL; frames[2] = NULL; - + uint8 uiPacketType = Buffer.data()[8]; if ( (Buffer.size() == 72) && ((uiPacketType == 1) || (uiPacketType == 3)) ) { @@ -507,7 +508,7 @@ bool CDmrplusProtocol::IsValidDvFramePacket(const CIp &Ip, const CBuffer &Buffer uint8 uiVoiceSeq = (Buffer.data()[18] & 0x0F) - 7; // aka slot type //uint32 uiDstId = *(uint32 *)(&Buffer.data()[64]) & 0x00FFFFFF; //uint32 uiSrcId = *(uint32 *)(&Buffer.data()[68]) & 0x00FFFFFF; - + // crack payload uint8 dmrframe[33]; uint8 dmr3ambe[27]; @@ -526,17 +527,17 @@ bool CDmrplusProtocol::IsValidDvFramePacket(const CIp &Ip, const CBuffer &Buffer dmrsync[0] = dmrframe[13] & 0x0F; ::memcpy(&dmrsync[1], &dmrframe[14], 5); dmrsync[6] = dmrframe[19] & 0xF0; - + // and create 3 dv frames uint32 uiStreamId = IpToStreamId(Ip); // frame1 memcpy(dmrambe, &dmr3ambe[0], 9); frames[0] = new CDvFramePacket(dmrambe, dmrsync, uiStreamId, uiVoiceSeq, 1); - + // frame2 memcpy(dmrambe, &dmr3ambe[9], 9); frames[1] = new CDvFramePacket(dmrambe, dmrsync, uiStreamId, uiVoiceSeq, 2); - + // frame3 memcpy(dmrambe, &dmr3ambe[18], 9); if ( uiPacketType == 3 ) @@ -547,12 +548,12 @@ bool CDmrplusProtocol::IsValidDvFramePacket(const CIp &Ip, const CBuffer &Buffer { frames[2] = new CDvFramePacket(dmrambe, dmrsync, uiStreamId, uiVoiceSeq, 3); } - + // check valid = true; } } - + // done return valid; } @@ -578,7 +579,7 @@ bool CDmrplusProtocol::EncodeDvHeaderPacket(const CDvHeaderPacket &Packet, CBuff uint8 tag[] = { 0x00,0x00,0x00,0x00,0x02,0x00,0x00,0x00,0x02, 0x00,0x05,0x01,0x02,0x00,0x00,0x00 } ; Buffer->Set(tag, sizeof(tag)); - + // uiSeqId //Buffer->ReplaceAt(4, 2); // uiPktType @@ -603,7 +604,7 @@ bool CDmrplusProtocol::EncodeDvHeaderPacket(const CDvHeaderPacket &Packet, CBuff Buffer->ReplaceAt(38, LOBYTE(HIWORD(uiSrcId))); Buffer->ReplaceAt(40, HIBYTE(LOWORD(uiSrcId))); Buffer->ReplaceAt(42, LOBYTE(LOWORD(uiSrcId))); - + // reserved Buffer->Append((uint16)0x0000); // uiCallType @@ -614,7 +615,7 @@ bool CDmrplusProtocol::EncodeDvHeaderPacket(const CDvHeaderPacket &Packet, CBuff Buffer->Append(uiDstId); // uiSrcId Buffer->Append(uiSrcId); - + // done return true; } @@ -624,11 +625,11 @@ void CDmrplusProtocol::EncodeDvPacket const CDvFramePacket &DvFrame0, const CDvFramePacket &DvFrame1, const CDvFramePacket &DvFrame2, uint8 seqid, CBuffer *Buffer) const { - + uint8 tag[] = { 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01, 0x00,0x05,0x01,0x02,0x00,0x00,0x00 } ; Buffer->Set(tag, sizeof(tag)); - + // uiSeqId Buffer->ReplaceAt(4, seqid); // uiPktType @@ -647,7 +648,7 @@ void CDmrplusProtocol::EncodeDvPacket Buffer->Append((uint16)0x1111); // reserved Buffer->Append((uint16)0x0000); - + // payload uint32 uiSrcId = Header.GetMyCallsign().GetDmrid() & 0x00FFFFFF; uint32 uiDstId = ModuleToDmrDestId(Header.GetRpt2Module()) & 0x00FFFFFF; @@ -735,7 +736,7 @@ uint32 CDmrplusProtocol::ModuleToDmrDestId(char m) const void CDmrplusProtocol::AppendVoiceLCToBuffer(CBuffer *buffer, uint32 uiSrcId) const { uint8 payload[34]; - + // fill payload CBPTC19696 bptc; ::memset(payload, 0, sizeof(payload)); @@ -770,11 +771,11 @@ void CDmrplusProtocol::AppendVoiceLCToBuffer(CBuffer *buffer, uint32 uiSrcId) co payload[13U] = (payload[13U] & 0x0FU) | ((slottype[0U] << 6) & 0xC0U) | ((slottype[1U] >> 2) & 0x30U); payload[19U] = (payload[19U] & 0xF0U) | ((slottype[1U] >> 2) & 0x0FU); payload[20U] = (payload[20U] & 0x03U) | ((slottype[1U] << 6) & 0xC0U) | ((slottype[2U] >> 2) & 0x3CU); - + } // and encode bptc.encode(lc, payload); - + // and append buffer->Append(payload, sizeof(payload)); } diff --git a/src/cdplusprotocol.cpp b/src/cdplusprotocol.cpp index 86aa4fb..95e93ac 100644 --- a/src/cdplusprotocol.cpp +++ b/src/cdplusprotocol.cpp @@ -4,6 +4,7 @@ // // Created by Jean-Luc Deltombe (LX3JL) on 01/11/2015. // Copyright © 2015 Jean-Luc Deltombe (LX3JL). All rights reserved. +// Copyright © 2020 Thomas A. Early, N7TAE // // ---------------------------------------------------------------------------- // This file is part of xlxd. @@ -19,7 +20,7 @@ // GNU General Public License for more details. // // You should have received a copy of the GNU General Public License -// along with Foobar. If not, see . +// along with Foobar. If not, see . // ---------------------------------------------------------------------------- #include "main.h" @@ -36,23 +37,23 @@ bool CDplusProtocol::Init(void) { bool ok; - + // base class ok = CProtocol::Init(); - + // update the reflector callsign m_ReflectorCallsign.PatchCallsign(0, (const uint8 *)"REF", 3); - + // create our socket ok &= m_Socket.Open(DPLUS_PORT); if ( !ok ) { std::cout << "Error opening socket on port UDP" << DPLUS_PORT << " on ip " << g_Reflector.GetListenIp() << std::endl; } - + // update time m_LastKeepaliveTime.Now(); - + // done return ok; } @@ -70,7 +71,7 @@ void CDplusProtocol::Task(void) CDvHeaderPacket *Header; CDvFramePacket *Frame; CDvLastFramePacket *LastFrame; - + // handle incoming packets if ( m_Socket.Receive(&Buffer, &Ip, 20) != -1 ) { @@ -78,14 +79,14 @@ void CDplusProtocol::Task(void) if ( (Frame = IsValidDvFramePacket(Buffer)) != NULL ) { //std::cout << "DPlus DV frame" << std::endl; - + // handle it OnDvFramePacketIn(Frame, &Ip); } else if ( (Header = IsValidDvHeaderPacket(Buffer)) != NULL ) { //std::cout << "DPlus DV header:" << std::endl << *Header << std::endl; - + // callsign muted? if ( g_GateKeeper.MayTransmit(Header->GetMyCallsign(), Ip, PROTOCOL_DPLUS, Header->GetRpt2Module()) ) { @@ -100,7 +101,7 @@ void CDplusProtocol::Task(void) else if ( (LastFrame = IsValidDvLastFramePacket(Buffer)) != NULL ) { //std::cout << "DPlus DV last frame" << std::endl; - + // handle it OnDvLastFramePacketIn(LastFrame, &Ip); } @@ -114,17 +115,17 @@ void CDplusProtocol::Task(void) else if ( IsValidLoginPacket(Buffer, &Callsign) ) { std::cout << "DPlus login packet from " << Callsign << " at " << Ip << std::endl; - + // callsign authorized? if ( g_GateKeeper.MayLink(Callsign, Ip, PROTOCOL_DPLUS) ) { // acknowledge the request EncodeLoginAckPacket(&Buffer); m_Socket.Send(Buffer, Ip); - + // create the client CDplusClient *client = new CDplusClient(Callsign, Ip); - + // and append g_Reflector.GetClients()->AddClient(client); g_Reflector.ReleaseClients(); @@ -135,12 +136,12 @@ void CDplusProtocol::Task(void) EncodeLoginNackPacket(&Buffer); m_Socket.Send(Buffer, Ip); } - + } else if ( IsValidDisconnectPacket(Buffer) ) { std::cout << "DPlus disconnect packet from " << Ip << std::endl; - + // find client CClients *clients = g_Reflector.GetClients(); CClient *client = clients->FindClient(Ip, PROTOCOL_DPLUS); @@ -157,12 +158,12 @@ void CDplusProtocol::Task(void) else if ( IsValidKeepAlivePacket(Buffer) ) { //std::cout << "DPlus keepalive packet from " << Ip << std::endl; - + // find all clients with that callsign & ip and keep them alive CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(Ip, PROTOCOL_DPLUS, &index)) != NULL ) + while ( (client = clients->FindNextClient(Ip, PROTOCOL_DPLUS, it)) != NULL ) { client->Alive(); } @@ -173,19 +174,19 @@ void CDplusProtocol::Task(void) std::cout << "DPlus packet (" << Buffer.size() << ")" << std::endl; } } - + // handle end of streaming timeout CheckStreamsTimeout(); - + // handle queue from reflector HandleQueue(); - + // keep client alive if ( m_LastKeepaliveTime.DurationSinceNow() > DPLUS_KEEPALIVE_PERIOD ) { // HandleKeepalives(); - + // update time m_LastKeepaliveTime.Now(); } @@ -197,14 +198,14 @@ void CDplusProtocol::Task(void) bool CDplusProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) { bool newstream = false; - + // find the stream CPacketStream *stream = GetStream(Header->GetStreamId()); if ( stream == NULL ) { // no stream open yet, open a new one CCallsign via(Header->GetRpt1Callsign()); - + // first, check module is valid if ( g_Reflector.IsValidModule(Header->GetRpt1Module()) ) { @@ -234,11 +235,11 @@ bool CDplusProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) } // release g_Reflector.ReleaseClients(); - + // update last heard g_Reflector.GetUsers()->Hearing(Header->GetMyCallsign(), via, Header->GetRpt2Callsign()); g_Reflector.ReleaseUsers(); - + // delete header if needed if ( !newstream ) { @@ -258,7 +259,7 @@ bool CDplusProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) // and delete packet delete Header; } - + // done return newstream; } @@ -274,10 +275,10 @@ void CDplusProtocol::HandleQueue(void) // get the packet CPacket *packet = m_Queue.front(); m_Queue.pop(); - + // get our sender's id int iModId = g_Reflector.GetModuleIndex(packet->GetModuleId()); - + // check if it's header and update cache if ( packet->IsDvHeader() ) { @@ -294,9 +295,9 @@ void CDplusProtocol::HandleQueue(void) // note that for dplus protocol, all stream of all modules are push to all clients // it's client who decide which stream he's interrrested in CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DPLUS, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DPLUS, it)) != NULL ) { // is this client busy ? if ( !client->IsAMaster() ) @@ -332,8 +333,8 @@ void CDplusProtocol::HandleQueue(void) } g_Reflector.ReleaseClients(); } - - + + // done delete packet; } @@ -368,13 +369,13 @@ void CDplusProtocol::SendDvHeader(CDvHeaderPacket *packet, CDplusClient *client) // no, send also the genuine packet m_Socket.Send(buffer, client->GetIp()); } - } + } else { // otherwise, send the original packet m_Socket.Send(buffer, client->GetIp()); } - } + } } //////////////////////////////////////////////////////////////////////////////////////// @@ -385,17 +386,17 @@ void CDplusProtocol::HandleKeepalives(void) // send keepalives CBuffer keepalive; EncodeKeepAlivePacket(&keepalive); - + // iterate on clients CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_DPLUS, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_DPLUS, it)) != NULL ) { // send keepalive //std::cout << "Sending DPlus packet @ " << client->GetIp() << std::endl; m_Socket.Send(keepalive, client->GetIp()); - + // is this client busy ? if ( client->IsAMaster() ) { @@ -409,7 +410,7 @@ void CDplusProtocol::HandleKeepalives(void) CBuffer disconnect; EncodeDisconnectPacket(&disconnect); m_Socket.Send(disconnect, client->GetIp()); - + // and remove it std::cout << "DPlus client " << client->GetCallsign() << " keepalive timeout" << std::endl; clients->RemoveClient(client); @@ -431,7 +432,7 @@ bool CDplusProtocol::IsValidLoginPacket(const CBuffer &Buffer, CCallsign *Callsi { uint8 Tag[] = { 0x1C,0xC0,0x04,0x00 }; bool valid = false; - + if ( (Buffer.size() == 28) &&(::memcmp(Buffer.data(), Tag, sizeof(Tag)) == 0) ) { Callsign->SetCallsign(&(Buffer.data()[4]), 8); @@ -455,7 +456,7 @@ bool CDplusProtocol::IsValidKeepAlivePacket(const CBuffer &Buffer) CDvHeaderPacket *CDplusProtocol::IsValidDvHeaderPacket(const CBuffer &Buffer) { CDvHeaderPacket *header = NULL; - + if ( (Buffer.size() == 58) && (Buffer.data()[0] == 0x3A) && (Buffer.data()[1] == 0x80) && (Buffer.Compare((uint8 *)"DSVT", 2, 4) == 0) && @@ -477,7 +478,7 @@ CDvHeaderPacket *CDplusProtocol::IsValidDvHeaderPacket(const CBuffer &Buffer) CDvFramePacket *CDplusProtocol::IsValidDvFramePacket(const CBuffer &Buffer) { CDvFramePacket *dvframe = NULL; - + if ( (Buffer.size() == 29) && (Buffer.data()[0] == 0x1D) && (Buffer.data()[1] == 0x80) && (Buffer.Compare((uint8 *)"DSVT", 2, 4) == 0) && @@ -499,7 +500,7 @@ CDvFramePacket *CDplusProtocol::IsValidDvFramePacket(const CBuffer &Buffer) CDvLastFramePacket *CDplusProtocol::IsValidDvLastFramePacket(const CBuffer &Buffer) { CDvLastFramePacket *dvframe = NULL; - + if ( (Buffer.size() == 32) && (Buffer.Compare((uint8 *)"DSVT", 2, 4) == 0) && (Buffer.data()[0] == 0x20) && (Buffer.data()[1] == 0x80) && @@ -551,9 +552,9 @@ bool CDplusProtocol::EncodeDvHeaderPacket(const CDvHeaderPacket &Packet, CBuffer { uint8 tag[] = { 0x3A,0x80,0x44,0x53,0x56,0x54,0x10,0x00,0x00,0x00,0x20,0x00,0x01,0x02 }; struct dstar_header DstarHeader; - + Packet.ConvertToDstarStruct(&DstarHeader); - + Buffer->Set(tag, sizeof(tag)); Buffer->Append(Packet.GetStreamId()); Buffer->Append((uint8)0x80); @@ -571,9 +572,9 @@ bool CDplusProtocol::EncodeDvFramePacket(const CDvFramePacket &Packet, CBuffer * Buffer->Append((uint8)(Packet.GetPacketId() % 21)); Buffer->Append((uint8 *)Packet.GetAmbe(), AMBE_SIZE); Buffer->Append((uint8 *)Packet.GetDvData(), DVDATA_SIZE); - + return true; - + } bool CDplusProtocol::EncodeDvLastFramePacket(const CDvLastFramePacket &Packet, CBuffer *Buffer) const @@ -585,6 +586,6 @@ bool CDplusProtocol::EncodeDvLastFramePacket(const CDvLastFramePacket &Packet, C Buffer->Append(Packet.GetStreamId()); Buffer->Append((uint8)((Packet.GetPacketId() % 21) | 0x40)); Buffer->Append(tag2, sizeof(tag2)); - - return true; + + return true; } diff --git a/src/cg3protocol.cpp b/src/cg3protocol.cpp index 053da9d..72b6f8f 100644 --- a/src/cg3protocol.cpp +++ b/src/cg3protocol.cpp @@ -4,6 +4,7 @@ // // Created by Marius Petrescu (YO2LOJ) on 03/06/2019. // Copyright © 2019 Marius Petrescu (YO2LOJ). All rights reserved. +// Copyright © 2020 Thomas A. Early, N7TAE // // ---------------------------------------------------------------------------- // This file is part of xlxd. @@ -19,7 +20,7 @@ // GNU General Public License for more details. // // You should have received a copy of the GNU General Public License -// along with Foobar. If not, see . +// along with Foobar. If not, see . // ---------------------------------------------------------------------------- #include "main.h" @@ -167,7 +168,7 @@ void CG3Protocol::PresenceTask(void) Owner.SetCallsign(&Buffer.data()[16], 8); Terminal.SetCallsign(&Buffer.data()[24], 8); - std::cout << "Presence from " << Ip << " as " << Callsign << " on terminal " << Terminal << std::endl; + std::cout << "Presence from " << Ip << " as " << Callsign << " on terminal " << Terminal << std::endl; // accept Buffer.data()[2] = 0x80; // response @@ -175,7 +176,7 @@ void CG3Protocol::PresenceTask(void) if (m_GwAddress == 0) { - Buffer.Append(*(uint32 *)m_ConfigSocket.GetLocalAddr()); + Buffer.Append(*(uint32 *)m_ConfigSocket.GetLocalAddr()); } else { @@ -183,10 +184,9 @@ void CG3Protocol::PresenceTask(void) } CClients *clients = g_Reflector.GetClients(); - - int index = -1; + auto it = clients->begin(); CClient *extant = NULL; - while ( (extant = clients->FindNextClient(PROTOCOL_G3, &index)) != NULL ) + while ( (extant = clients->FindNextClient(PROTOCOL_G3, it)) != NULL ) { CIp ClIp = extant->GetIp(); if (ClIp.GetAddr() == Ip.GetAddr()) @@ -197,10 +197,10 @@ void CG3Protocol::PresenceTask(void) if (extant == NULL) { - index = -1; - + it = clients->begin(); + // do we already have a client with the same call (IP changed)? - while ( (extant = clients->FindNextClient(PROTOCOL_G3, &index)) != NULL ) + while ( (extant = clients->FindNextClient(PROTOCOL_G3, it)) != NULL ) { { if (extant->GetCallsign().HasSameCallsign(Terminal)) @@ -328,7 +328,7 @@ void CG3Protocol::ConfigTask(void) if (m_GwAddress == 0) { - Buffer.Append(*(uint32 *)m_ConfigSocket.GetLocalAddr()); + Buffer.Append(*(uint32 *)m_ConfigSocket.GetLocalAddr()); } else { @@ -359,10 +359,9 @@ void CG3Protocol::IcmpTask(void) if (iIcmpType == ICMP_DEST_UNREACH) { CClients *clients = g_Reflector.GetClients(); - - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_G3, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_G3, it)) != NULL ) { CIp ClientIp = client->GetIp(); if (ClientIp.GetAddr() == Ip.GetAddr()) @@ -396,9 +395,9 @@ void CG3Protocol::Task(void) CIp ClIp; CIp *BaseIp = NULL; CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_G3, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_G3, it)) != NULL ) { ClIp = client->GetIp(); if (ClIp.GetAddr() == Ip.GetAddr()) @@ -491,16 +490,16 @@ void CG3Protocol::HandleQueue(void) // get the packet CPacket *packet = m_Queue.front(); m_Queue.pop(); - + // encode it CBuffer buffer; if ( EncodeDvPacket(*packet, &buffer) ) { // and push it to all our clients linked to the module and who are not streaming in CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_G3, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_G3, it)) != NULL ) { // is this client busy ? if ( !client->IsAMaster() && (client->GetReflectorModule() == packet->GetModuleId()) ) @@ -515,7 +514,7 @@ void CG3Protocol::HandleQueue(void) } g_Reflector.ReleaseClients(); } - + // done delete packet; } @@ -534,9 +533,9 @@ void CG3Protocol::HandleKeepalives(void) // iterate on clients CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_G3, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_G3, it)) != NULL ) { if (!client->IsAlive()) { @@ -568,10 +567,9 @@ bool CG3Protocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) // find this client CClients *clients = g_Reflector.GetClients(); - - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_G3, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_G3, it)) != NULL ) { CIp ClIp = client->GetIp(); if (ClIp.GetAddr() == Ip.GetAddr()) @@ -653,7 +651,7 @@ bool CG3Protocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) CDvHeaderPacket *CG3Protocol::IsValidDvHeaderPacket(const CBuffer &Buffer) { CDvHeaderPacket *header = NULL; - + if ( (Buffer.size() == 56) && (Buffer.Compare((uint8 *)"DSVT", 4) == 0) && (Buffer.data()[4] == 0x10) && (Buffer.data()[8] == 0x20) ) { @@ -673,7 +671,7 @@ CDvHeaderPacket *CG3Protocol::IsValidDvHeaderPacket(const CBuffer &Buffer) CDvFramePacket *CG3Protocol::IsValidDvFramePacket(const CBuffer &Buffer) { CDvFramePacket *dvframe = NULL; - + if ( (Buffer.size() == 27) && (Buffer.Compare((uint8 *)"DSVT", 4) == 0) && (Buffer.data()[4] == 0x20) && (Buffer.data()[8] == 0x20) && ((Buffer.data()[14] & 0x40) == 0) ) @@ -694,7 +692,7 @@ CDvFramePacket *CG3Protocol::IsValidDvFramePacket(const CBuffer &Buffer) CDvLastFramePacket *CG3Protocol::IsValidDvLastFramePacket(const CBuffer &Buffer) { CDvLastFramePacket *dvframe = NULL; - + if ( (Buffer.size() == 27) && (Buffer.Compare((uint8 *)"DSVT", 4) == 0) && (Buffer.data()[4] == 0x20) && (Buffer.data()[8] == 0x20) && ((Buffer.data()[14] & 0x40) != 0) ) @@ -719,41 +717,41 @@ bool CG3Protocol::EncodeDvHeaderPacket(const CDvHeaderPacket &Packet, CBuffer *B { uint8 tag[] = { 'D','S','V','T',0x10,0x00,0x00,0x00,0x20,0x00,0x01,0x02 }; struct dstar_header DstarHeader; - + Packet.ConvertToDstarStruct(&DstarHeader); - + Buffer->Set(tag, sizeof(tag)); Buffer->Append(Packet.GetStreamId()); Buffer->Append((uint8)0x80); Buffer->Append((uint8 *)&DstarHeader, sizeof(struct dstar_header)); - + return true; } bool CG3Protocol::EncodeDvFramePacket(const CDvFramePacket &Packet, CBuffer *Buffer) const { uint8 tag[] = { 'D','S','V','T',0x20,0x00,0x00,0x00,0x20,0x00,0x01,0x02 }; - + Buffer->Set(tag, sizeof(tag)); Buffer->Append(Packet.GetStreamId()); Buffer->Append((uint8)(Packet.GetPacketId() % 21)); Buffer->Append((uint8 *)Packet.GetAmbe(), AMBE_SIZE); Buffer->Append((uint8 *)Packet.GetDvData(), DVDATA_SIZE); - + return true; - + } bool CG3Protocol::EncodeDvLastFramePacket(const CDvLastFramePacket &Packet, CBuffer *Buffer) const { uint8 tag1[] = { 'D','S','V','T',0x20,0x00,0x00,0x00,0x20,0x00,0x01,0x02 }; uint8 tag2[] = { 0x55,0xC8,0x7A,0x00,0x00,0x00,0x00,0x00,0x00,0x25,0x1A,0xC6 }; - + Buffer->Set(tag1, sizeof(tag1)); Buffer->Append(Packet.GetStreamId()); Buffer->Append((uint8)((Packet.GetPacketId() % 21) | 0x40)); Buffer->Append(tag2, sizeof(tag2)); - + return true; } @@ -785,9 +783,9 @@ void CG3Protocol::NeedReload(void) // we have new options - iterate on clients for potential removal CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_G3, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_G3, it)) != NULL ) { char module = client->GetReflectorModule(); if (!strchr(m_Modules.c_str(), module) && !strchr(m_Modules.c_str(), '*')) @@ -858,4 +856,3 @@ void CG3Protocol::ReadOptions(void) } } } - diff --git a/src/creflector.cpp b/src/creflector.cpp index 2eeea8b..80257bb 100644 --- a/src/creflector.cpp +++ b/src/creflector.cpp @@ -103,19 +103,19 @@ bool CReflector::Start(void) // init gate keeper ok &= g_GateKeeper.Init(); - + // init dmrid directory g_DmridDir.Init(); - + // init wiresx node directory g_YsfNodeDir.Init(); - + // init the transcoder g_Transcoder.Init(); - + // create protocols ok &= m_Protocols.Init(); - + // if ok, start threads if ( ok ) { @@ -135,7 +135,7 @@ bool CReflector::Start(void) { m_Protocols.Close(); } - + // done return ok; } @@ -175,10 +175,10 @@ void CReflector::Stop(void) // close transcoder g_Transcoder.Close(); - + // close gatekeeper g_GateKeeper.Close(); - + // close databases g_DmridDir.Close(); g_YsfNodeDir.Close(); @@ -196,10 +196,10 @@ bool CReflector::IsStreaming(char module) CPacketStream *CReflector::OpenStream(CDvHeaderPacket *DvHeader, CClient *client) { CPacketStream *retStream = NULL; - + // clients MUST have bee locked by the caller // so we can freely access it within the fuction - + // check sid is not NULL if ( DvHeader->GetStreamId() != 0 ) { @@ -223,21 +223,21 @@ CPacketStream *CReflector::OpenStream(CDvHeaderPacket *DvHeader, CClient *client // stream open, mark client as master // so that it can't be deleted client->SetMasterOfModule(module); - + // update last heard time client->Heard(); retStream = stream; - + // and push header packet stream->Push(DvHeader); - + // report std::cout << "Opening stream on module " << module << " for client " << client->GetCallsign() << " with sid " << DvHeader->GetStreamId() << std::endl; - + // notify g_Reflector.OnStreamOpen(stream->GetUserCallsign()); - + } // unlock now stream->Unlock(); @@ -251,7 +251,7 @@ CPacketStream *CReflector::OpenStream(CDvHeaderPacket *DvHeader, CClient *client } } } - + // done return retStream; } @@ -278,10 +278,10 @@ void CReflector::CloseStream(CPacketStream *stream) CTimePoint::TaskSleepFor(10); } } while (!bEmpty); - + // lock clients GetClients(); - + // lock stream stream->Lock(); @@ -300,12 +300,12 @@ void CReflector::CloseStream(CPacketStream *stream) // release clients ReleaseClients(); - + // unlock before closing // to avoid double lock in assiociated // codecstream close/thread-join stream->Unlock(); - + // and stop the queue stream->Close(); @@ -509,7 +509,7 @@ void CReflector::JsonReportThread(CReflector *This) void CReflector::OnPeersChanged(void) { CNotification notification(NOTIFICATION_PEERS); - + m_Notifications.Lock(); m_Notifications.push(notification); m_Notifications.Unlock(); @@ -606,12 +606,12 @@ void CReflector::WriteXmlFile(std::ofstream &xmlFile) { // write header xmlFile << "" << std::endl; - + // software version char sz[64]; ::sprintf(sz, "%d.%d.%d", VERSION_MAJOR, VERSION_MINOR, VERSION_REVISION); xmlFile << "" << sz << "" << std::endl; - + // linked peers xmlFile << "<" << m_Callsign << "linked peers>" << std::endl; // lock @@ -624,23 +624,23 @@ void CReflector::WriteXmlFile(std::ofstream &xmlFile) // unlock ReleasePeers(); xmlFile << "" << std::endl; - + // linked nodes xmlFile << "<" << m_Callsign << "linked nodes>" << std::endl; // lock CClients *clients = GetClients(); // iterate on clients - for ( int i = 0; i < clients->GetSize(); i++ ) + for ( auto it=clients->cbegin(); it!=clients->cend(); it++ ) { - if ( clients->GetClient(i)->IsNode() ) + if ( (*it)->IsNode() ) { - clients->GetClient(i)->WriteXml(xmlFile); + (*it)->WriteXml(xmlFile); } } // unlock ReleaseClients(); xmlFile << "" << std::endl; - + // last heard users xmlFile << "<" << m_Callsign << "heard users>" << std::endl; // lock @@ -696,10 +696,10 @@ void CReflector::SendJsonNodesObject(CUdpSocket &Socket, CIp &Ip) // lock CClients *clients = GetClients(); // iterate on clients - for ( int i = 0; (i < clients->GetSize()) && (i < JSON_NBMAX_NODES); i++ ) + for ( auto it=clients->cbegin(); it!=clients->cend(); ) { - clients->GetClient(i)->GetJsonObject(Buffer); - if ( i < clients->GetSize()-1 ) + (*it++)->GetJsonObject(Buffer); + if ( it != clients->cend() ) { ::strcat(Buffer, ","); } diff --git a/src/cxlxprotocol.cpp b/src/cxlxprotocol.cpp index ab029b3..06927af 100644 --- a/src/cxlxprotocol.cpp +++ b/src/cxlxprotocol.cpp @@ -271,9 +271,9 @@ void CXlxProtocol::HandleQueue(void) // and push it to all our clients linked to the module and who are not streaming in CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_XLX, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_XLX, it)) != NULL ) { // is this client busy ? if ( !client->IsAMaster() && (client->GetReflectorModule() == packet->GetModuleId()) ) diff --git a/src/cysfprotocol.cpp b/src/cysfprotocol.cpp index f0573a3..208fbe4 100644 --- a/src/cysfprotocol.cpp +++ b/src/cysfprotocol.cpp @@ -4,6 +4,7 @@ // // Created by Jean-Luc Deltombe (LX3JL) on 20/05/2018. // Copyright © 2015 Jean-Luc Deltombe (LX3JL). All rights reserved. +// Copyright © 2020 Thomas A. Early, N7TAE // // ---------------------------------------------------------------------------- // This file is part of xlxd. @@ -47,26 +48,26 @@ CYsfProtocol::CYsfProtocol() bool CYsfProtocol::Init(void) { bool ok; - + // base class ok = CProtocol::Init(); - + // update the reflector callsign m_ReflectorCallsign.PatchCallsign(0, (const uint8 *)"YSF", 3); - + // create our socket ok &= m_Socket.Open(YSF_PORT); if ( !ok ) { std::cout << "Error opening socket on port UDP" << YSF_PORT << " on ip " << g_Reflector.GetListenIp() << std::endl; } - + // init the wiresx cmd handler ok &= m_WiresxCmdHandler.Init(); - + // update time m_LastKeepaliveTime.Now(); - + // done return ok; } @@ -75,7 +76,7 @@ void CYsfProtocol::Close(void) { // base class CProtocol::Close(); - + // and close wiresx handler m_WiresxCmdHandler.Close(); } @@ -92,7 +93,7 @@ void CYsfProtocol::Task(void) CDvHeaderPacket *Header; CDvFramePacket *Frames[5]; CWiresxCmd WiresxCmd; - + int iWiresxCmd; int iWiresxArg; @@ -108,7 +109,7 @@ void CYsfProtocol::Task(void) } m_WiresxCmdHandler.ReleasePacketQueue(); } - + // handle incoming packets if ( m_Socket.Receive(&Buffer, &Ip, 20) != -1 ) { @@ -119,7 +120,7 @@ void CYsfProtocol::Task(void) if ( IsValidDvFramePacket(Ip, Fich, Buffer, Frames) ) { //std::cout << "YSF DV frame" << std::endl; - + // handle it OnDvFramePacketIn(Frames[0], &Ip); OnDvFramePacketIn(Frames[1], &Ip); @@ -131,7 +132,7 @@ void CYsfProtocol::Task(void) { //std::cout << "YSF DV header:" << std::endl << *Header << std::endl; //std::cout << "YSF DV header:" << std::endl; - + // node linked and callsign muted? if ( g_GateKeeper.MayTransmit(Header->GetMyCallsign(), Ip, PROTOCOL_YSF, Header->GetRpt2Module()) ) { @@ -157,14 +158,14 @@ void CYsfProtocol::Task(void) else if ( IsValidConnectPacket(Buffer, &Callsign) ) { //std::cout << "YSF keepalive/connect packet from " << Callsign << " at " << Ip << std::endl; - + // callsign authorized? if ( g_GateKeeper.MayLink(Callsign, Ip, PROTOCOL_YSF) ) { // acknowledge the request EncodeConnectAckPacket(&Buffer); m_Socket.Send(Buffer, Ip); - + // add client if needed CClients *clients = g_Reflector.GetClients(); CClient *client = clients->FindClient(Callsign, Ip, PROTOCOL_YSF); @@ -172,15 +173,15 @@ void CYsfProtocol::Task(void) if ( client == NULL ) { std::cout << "YSF connect packet from " << Callsign << " at " << Ip << std::endl; - + // create the client CYsfClient *newclient = new CYsfClient(Callsign, Ip); - + // aautolink, if enabled #if YSF_AUTOLINK_ENABLE newclient->SetReflectorModule(YSF_AUTOLINK_MODULE); #endif - + // and append clients->AddClient(newclient); } @@ -215,19 +216,19 @@ void CYsfProtocol::Task(void) //Buffer.DebugDump(g_Reflector.m_DebugFile); } } - + // handle end of streaming timeout CheckStreamsTimeout(); - + // handle queue from reflector HandleQueue(); - + // keep client alive if ( m_LastKeepaliveTime.DurationSinceNow() > YSF_KEEPALIVE_PERIOD ) { // HandleKeepalives(); - + // update time m_LastKeepaliveTime.Now(); } @@ -239,14 +240,14 @@ void CYsfProtocol::Task(void) bool CYsfProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) { bool newstream = false; - + // find the stream CPacketStream *stream = GetStream(Header->GetStreamId()); if ( stream == NULL ) { // no stream open yet, open a new one CCallsign via(Header->GetRpt1Callsign()); - + // find this client CClient *client = g_Reflector.GetClients()->FindClient(Ip, PROTOCOL_YSF); if ( client != NULL ) @@ -266,14 +267,14 @@ bool CYsfProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) } // release g_Reflector.ReleaseClients(); - + // update last heard if ( g_Reflector.IsValidModule(Header->GetRpt2Module()) ) { g_Reflector.GetUsers()->Hearing(Header->GetMyCallsign(), via, Header->GetRpt2Callsign()); g_Reflector.ReleaseUsers(); } - + // delete header if needed if ( !newstream ) { @@ -288,7 +289,7 @@ bool CYsfProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) // and delete packet delete Header; } - + // done return newstream; } @@ -298,27 +299,27 @@ bool CYsfProtocol::OnDvHeaderPacketIn(CDvHeaderPacket *Header, const CIp &Ip) void CYsfProtocol::HandleQueue(void) { - + m_Queue.Lock(); while ( !m_Queue.empty() ) { // get the packet CPacket *packet = m_Queue.front(); m_Queue.pop(); - + // get our sender's id int iModId = g_Reflector.GetModuleIndex(packet->GetModuleId()); - + // encode CBuffer buffer; - + // check if it's header if ( packet->IsDvHeader() ) { // update local stream cache // this relies on queue feeder setting valid module id m_StreamsCache[iModId].m_dvHeader = CDvHeaderPacket((const CDvHeaderPacket &)*packet); - + // encode it EncodeDvHeaderPacket((const CDvHeaderPacket &)*packet, &buffer); } @@ -339,32 +340,32 @@ void CYsfProtocol::HandleQueue(void) m_StreamsCache[iModId].m_dvFrames[sid] = CDvFramePacket((const CDvFramePacket &)*packet); if ( sid == 4 ) { - + EncodeDvPacket(m_StreamsCache[iModId].m_dvHeader, m_StreamsCache[iModId].m_dvFrames, &buffer); } } } - + // send it if ( buffer.size() > 0 ) { // and push it to all our clients linked to the module and who are not streaming in CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_YSF, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_YSF, it)) != NULL ) { // is this client busy ? if ( !client->IsAMaster() && (client->GetReflectorModule() == packet->GetModuleId()) ) { // no, send the packet m_Socket.Send(buffer, client->GetIp()); - + } } g_Reflector.ReleaseClients(); } - + // done delete packet; } @@ -379,12 +380,12 @@ void CYsfProtocol::HandleKeepalives(void) // YSF protocol keepalive request is client tasks // here, just check that all clients are still alive // and disconnect them if not - + // iterate on clients CClients *clients = g_Reflector.GetClients(); - int index = -1; + auto it = clients->begin(); CClient *client = NULL; - while ( (client = clients->FindNextClient(PROTOCOL_YSF, &index)) != NULL ) + while ( (client = clients->FindNextClient(PROTOCOL_YSF, it)) != NULL ) { // is this client busy ? if ( client->IsAMaster() ) @@ -399,7 +400,7 @@ void CYsfProtocol::HandleKeepalives(void) std::cout << "YSF client " << client->GetCallsign() << " keepalive timeout" << std::endl; clients->RemoveClient(client); } - + } g_Reflector.ReleaseClients(); } @@ -424,7 +425,7 @@ bool CYsfProtocol::IsValidConnectPacket(const CBuffer &Buffer, CCallsign *callsi bool CYsfProtocol::IsValidDvPacket(const CBuffer &Buffer, CYSFFICH *Fich) { uint8 tag[] = { 'Y','S','F','D' }; - + bool valid = false; if ( (Buffer.size() == 155) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) @@ -451,7 +452,7 @@ bool CYsfProtocol::IsValidDvHeaderPacket(const CIp &Ip, const CYSFFICH &Fich, co { // get stream id uint32 uiStreamId = IpToStreamId(Ip); - + // get header data CYSFPayload ysfPayload; if ( ysfPayload.processHeaderData((unsigned char *)&(Buffer.data()[35])) ) @@ -470,7 +471,7 @@ bool CYsfProtocol::IsValidDvHeaderPacket(const CIp &Ip, const CYSFFICH &Fich, co // destid, set module to none and rely on OnDvHeaderPacketIn() // to later fill it with proper value rpt2.SetModule(' '); - + // and packet *header = new CDvHeaderPacket(csMY, CCallsign("CQCQCQ"), rpt1, rpt2, uiStreamId, Fich.getFN()); } @@ -481,7 +482,7 @@ bool CYsfProtocol::IsValidDvHeaderPacket(const CIp &Ip, const CYSFFICH &Fich, co frames[0] = new CDvFramePacket(uiAmbe, uiStreamId, Fich.getFN(), 0, 0); frames[1] = new CDvFramePacket(uiAmbe, uiStreamId, Fich.getFN(), 1, 0); } - + // check validity of packets if ( ((*header) == NULL) || !(*header)->IsValid() || (frames[0] == NULL) || !(frames[0]->IsValid()) || @@ -501,7 +502,7 @@ bool CYsfProtocol::IsValidDvHeaderPacket(const CIp &Ip, const CYSFFICH &Fich, co } } - + // done return valid; } @@ -514,13 +515,13 @@ bool CYsfProtocol::IsValidDvFramePacket(const CIp &Ip, const CYSFFICH &Fich, con frames[2] = NULL; frames[3] = NULL; frames[4] = NULL; - + // is it DV frame ? if ( Fich.getFI() == YSF_FI_COMMUNICATIONS ) { // get stream id uint32 uiStreamId = IpToStreamId(Ip); - + // get DV frames uint8 ambe0[AMBEPLUS_SIZE]; uint8 ambe1[AMBEPLUS_SIZE]; @@ -537,7 +538,7 @@ bool CYsfProtocol::IsValidDvFramePacket(const CIp &Ip, const CYSFFICH &Fich, con frames[2] = new CDvFramePacket(ambe2, uiStreamId, Fich.getFN(), 2, fid); frames[3] = new CDvFramePacket(ambe3, uiStreamId, Fich.getFN(), 3, fid); frames[4] = new CDvFramePacket(ambe4, uiStreamId, Fich.getFN(), 4, fid); - + // check validity of packets if ( (frames[0] == NULL) || !(frames[0]->IsValid()) || (frames[1] == NULL) || !(frames[1]->IsValid()) || @@ -571,13 +572,13 @@ bool CYsfProtocol::IsValidDvLastFramePacket(const CIp &Ip, const CYSFFICH &Fich, bool valid = false; frames[0] = NULL; frames[1] = NULL; - + // DV header ? if ( Fich.getFI() == YSF_FI_TERMINATOR ) { // get stream id uint32 uiStreamId = IpToStreamId(Ip); - + // get DV frames { uint8 uiAmbe[AMBE_SIZE]; @@ -585,11 +586,11 @@ bool CYsfProtocol::IsValidDvLastFramePacket(const CIp &Ip, const CYSFFICH &Fich, frames[0] = new CDvFramePacket(uiAmbe, uiStreamId, Fich.getFN(), 0, 0); frames[1] = new CDvLastFramePacket(uiAmbe, uiStreamId, Fich.getFN(), 1, 0); } - + // check validity of packets if ( (frames[0] == NULL) || !(frames[0]->IsValid()) || (frames[1] == NULL) || !(frames[1]->IsValid()) ) - + { delete frames[0]; delete frames[1]; @@ -601,7 +602,7 @@ bool CYsfProtocol::IsValidDvLastFramePacket(const CIp &Ip, const CYSFFICH &Fich, valid = true; } } - + // done return valid; } @@ -666,7 +667,7 @@ bool CYsfProtocol::EncodeDvHeaderPacket(const CDvHeaderPacket &Header, CBuffer * uint8 temp[120]; payload.writeHeader(temp, csd1, csd2); Buffer->Append(temp+30, 120-30); - + // done return true; } @@ -678,7 +679,7 @@ bool CYsfProtocol::EncodeDvPacket(const CDvHeaderPacket &Header, const CDvFrameP uint8 gps[] = { 0x52,0x22,0x61,0x5F,0x27,0x03,0x5E,0x20,0x20,0x20 }; char sz[YSF_CALLSIGN_LENGTH]; uint8 fichd[YSF_FICH_LENGTH_BYTES]; - + // tag Buffer->Set(tag, sizeof(tag)); // rpt1 @@ -769,7 +770,7 @@ bool CYsfProtocol::EncodeDvLastPacket(const CDvHeaderPacket &Header, CBuffer *Bu uint8 dest[] = { 'A','L','L',' ',' ',' ',' ',' ',' ',' ' }; char sz[YSF_CALLSIGN_LENGTH]; uint8 fichd[YSF_FICH_LENGTH_BYTES]; - + // tag Buffer->Set(tag, sizeof(tag)); // rpt1 @@ -813,7 +814,7 @@ bool CYsfProtocol::EncodeDvLastPacket(const CDvHeaderPacket &Header, CBuffer *Bu uint8 temp[120]; payload.writeHeader(temp, csd1, csd2); Buffer->Append(temp+30, 120-30); - + // done return true; } @@ -939,7 +940,7 @@ bool CYsfProtocol::IsValidwirexPacket(const CBuffer &Buffer, CYSFFICH *Fich, CCa bool CYsfProtocol::IsValidServerStatusPacket(const CBuffer &Buffer) const { uint8 tag[] = { 'Y','S','F','S' }; - + return ( (Buffer.size() >= 4) && (Buffer.Compare(tag, sizeof(tag)) == 0) ); } @@ -950,7 +951,7 @@ bool CYsfProtocol::EncodeServerStatusPacket(CBuffer *Buffer) const uint8 tag[] = { 'Y','S','F','S' }; uint8 description[] = { 'X','L','X',' ','r','e','f','l','e','c','t','o','r',' ' }; uint8 callsign[16]; - + // tag Buffer->Set(tag, sizeof(tag)); // hash @@ -969,7 +970,7 @@ bool CYsfProtocol::EncodeServerStatusPacket(CBuffer *Buffer) const g_Reflector.ReleaseClients(); ::sprintf(sz, "%03u", count); Buffer->Append((uint8 *)sz, 3); - + // done return true; } @@ -1015,7 +1016,7 @@ bool CYsfProtocol::DebugTestDecodePacket(const CBuffer &Buffer) CYSFPayload payload; CBuffer dump; bool valid = false; - + if ( (Buffer.size() == 155) && (Buffer.Compare(tag, sizeof(tag)) == 0) ) { // decode YSH fich @@ -1027,7 +1028,7 @@ bool CYsfProtocol::DebugTestDecodePacket(const CBuffer &Buffer) << (int)Fich.getBT() << "," << (int)Fich.getFN() << "," << (int)Fich.getFT() << " : "; - + switch ( Fich.getFI() ) { case YSF_FI_HEADER: @@ -1076,14 +1077,14 @@ bool CYsfProtocol::DebugDumpHeaderPacket(const CBuffer &Buffer) uint8 data[200]; :: memset(data, 0, sizeof(data)); - + ok = IsValidDvPacket(Buffer, &fich); if ( ok && (fich.getFI() == YSF_FI_HEADER) ) { ok &= payload.processHeaderData((unsigned char *)&(Buffer.data()[35])); } - + std::cout << "HD-" <<(ok ? "ok " : "xx ") << "src: " << payload.getSource() << "dest: " << payload.getDest() << std::endl; return ok; @@ -1105,7 +1106,7 @@ bool CYsfProtocol::DebugDumpDvPacket(const CBuffer &Buffer) } std::cout << "DV-" <<(ok ? "ok " : "xx ") << "FN:" << (int)fich.getFN() << " payload: " << (char *)data << std::endl; - + return ok; } @@ -1117,14 +1118,14 @@ bool CYsfProtocol::DebugDumpLastDvPacket(const CBuffer &Buffer) uint8 data[200]; :: memset(data, 0, sizeof(data)); - + ok = IsValidDvPacket(Buffer, &fich); if ( ok && (fich.getFI() == YSF_FI_TERMINATOR) ) { ok &= payload.processHeaderData((unsigned char *)&(Buffer.data()[35])); } - + std::cout << "TC-" <<(ok ? "ok " : "xx ") << "src: " << payload.getSource() << "dest: " << payload.getDest() << std::endl; return ok;