commit
6d27b8d957
122
DMRLookup.cpp
122
DMRLookup.cpp
|
@ -30,7 +30,6 @@ CThread(),
|
|||
m_filename(filename),
|
||||
m_reloadTime(reloadTime),
|
||||
m_table(),
|
||||
m_mutex(),
|
||||
m_stop(false)
|
||||
{
|
||||
}
|
||||
|
@ -41,7 +40,7 @@ CDMRLookup::~CDMRLookup()
|
|||
|
||||
bool CDMRLookup::read()
|
||||
{
|
||||
bool ret = load();
|
||||
bool ret = m_table.load(m_filename);
|
||||
|
||||
if (m_reloadTime > 0U)
|
||||
run();
|
||||
|
@ -61,7 +60,7 @@ void CDMRLookup::entry()
|
|||
|
||||
timer.clock();
|
||||
if (timer.hasExpired()) {
|
||||
load();
|
||||
m_table.load(m_filename);
|
||||
timer.start();
|
||||
}
|
||||
}
|
||||
|
@ -81,118 +80,47 @@ void CDMRLookup::stop()
|
|||
wait();
|
||||
}
|
||||
|
||||
std::string CDMRLookup::findWithName(unsigned int id)
|
||||
void CDMRLookup::findWithName(unsigned int id, class CUserDBentry *entry)
|
||||
{
|
||||
std::string callsign;
|
||||
|
||||
if (id == 0xFFFFFFU)
|
||||
return std::string("ALL");
|
||||
|
||||
m_mutex.lock();
|
||||
|
||||
try {
|
||||
callsign = m_table.at(id);
|
||||
LogDebug("FindWithName =%s",callsign.c_str());
|
||||
|
||||
} catch (...) {
|
||||
char text[10U];
|
||||
::sprintf(text, "%u", id);
|
||||
callsign = std::string(text);
|
||||
if (id == 0xFFFFFFU) {
|
||||
entry->clear();
|
||||
entry->set(keyCALLSIGN, "ALL");
|
||||
return;
|
||||
}
|
||||
|
||||
m_mutex.unlock();
|
||||
if (m_table.lookup(id, entry)) {
|
||||
LogDebug("FindWithName =%s %s", entry->get(keyCALLSIGN).c_str(), entry->get(keyFIRST_NAME).c_str());
|
||||
} else {
|
||||
entry->clear();
|
||||
|
||||
return callsign;
|
||||
char text[10U];
|
||||
::snprintf(text, sizeof(text), "%u", id);
|
||||
entry->set(keyCALLSIGN, text);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
std::string CDMRLookup::find(unsigned int id)
|
||||
{
|
||||
std::string callsign;
|
||||
std::string b;
|
||||
|
||||
|
||||
|
||||
if (id == 0xFFFFFFU)
|
||||
return std::string("ALL");
|
||||
|
||||
m_mutex.lock();
|
||||
|
||||
try {
|
||||
b = m_table.at(id);
|
||||
size_t n = b.find(" ");
|
||||
if (n > 0) {
|
||||
callsign = b.substr(0,n);
|
||||
|
||||
} else {
|
||||
LogDebug("b=%s",b.c_str());
|
||||
callsign = b;
|
||||
}
|
||||
|
||||
} catch (...) {
|
||||
class CUserDBentry entry;
|
||||
if (m_table.lookup(id, &entry)) {
|
||||
callsign = entry.get(keyCALLSIGN);
|
||||
} else {
|
||||
char text[10U];
|
||||
::sprintf(text, "%u", id);
|
||||
::snprintf(text, sizeof(text), "%u", id);
|
||||
callsign = std::string(text);
|
||||
}
|
||||
|
||||
m_mutex.unlock();
|
||||
|
||||
return callsign;
|
||||
}
|
||||
|
||||
bool CDMRLookup::exists(unsigned int id)
|
||||
{
|
||||
m_mutex.lock();
|
||||
|
||||
bool found = m_table.count(id) == 1U;
|
||||
|
||||
m_mutex.unlock();
|
||||
|
||||
return found;
|
||||
return m_table.lookup(id, NULL);
|
||||
}
|
||||
|
||||
bool CDMRLookup::load()
|
||||
{
|
||||
FILE* fp = ::fopen(m_filename.c_str(), "rt");
|
||||
if (fp == NULL) {
|
||||
LogWarning("Cannot open the DMR Id lookup file - %s", m_filename.c_str());
|
||||
return false;
|
||||
}
|
||||
|
||||
m_mutex.lock();
|
||||
|
||||
// Remove the old entries
|
||||
m_table.clear();
|
||||
|
||||
char buffer[100U];
|
||||
while (::fgets(buffer, 100U, fp) != NULL) {
|
||||
if (buffer[0U] == '#')
|
||||
continue;
|
||||
|
||||
char* p1 = ::strtok(buffer, " \t\r\n");
|
||||
char* p2 = ::strtok(NULL, " \r\n"); // tokenize to eol to capture name as well
|
||||
|
||||
if (p1 != NULL && p2 != NULL) {
|
||||
unsigned int id = (unsigned int)::atoi(p1);
|
||||
for (char* p = p2; *p != 0x00U; p++) {
|
||||
|
||||
if(*p == 0x09U)
|
||||
*p = 0x20U;
|
||||
|
||||
else
|
||||
*p = ::toupper(*p);
|
||||
|
||||
}
|
||||
m_table[id] = std::string(p2);
|
||||
}
|
||||
}
|
||||
|
||||
m_mutex.unlock();
|
||||
|
||||
::fclose(fp);
|
||||
|
||||
size_t size = m_table.size();
|
||||
if (size == 0U)
|
||||
return false;
|
||||
|
||||
LogInfo("Loaded %u Ids to the DMR callsign lookup table", size);
|
||||
|
||||
return true;
|
||||
}
|
16
DMRLookup.h
16
DMRLookup.h
|
@ -20,10 +20,9 @@
|
|||
#define DMRLookup_H
|
||||
|
||||
#include "Thread.h"
|
||||
#include "Mutex.h"
|
||||
#include "UserDB.h"
|
||||
|
||||
#include <string>
|
||||
#include <unordered_map>
|
||||
|
||||
class CDMRLookup : public CThread {
|
||||
public:
|
||||
|
@ -35,20 +34,17 @@ public:
|
|||
virtual void entry();
|
||||
|
||||
std::string find(unsigned int id);
|
||||
std::string findWithName(unsigned int id);
|
||||
void findWithName(unsigned int id, class CUserDBentry *entry);
|
||||
|
||||
bool exists(unsigned int id);
|
||||
|
||||
void stop();
|
||||
|
||||
private:
|
||||
std::string m_filename;
|
||||
unsigned int m_reloadTime;
|
||||
std::unordered_map<unsigned int, std::string> m_table;
|
||||
CMutex m_mutex;
|
||||
bool m_stop;
|
||||
|
||||
bool load();
|
||||
std::string m_filename;
|
||||
unsigned int m_reloadTime;
|
||||
class CUserDB m_table;
|
||||
bool m_stop;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1108,7 +1108,8 @@ void CDMRSlot::writeNetwork(const CDMRData& dmrData)
|
|||
setShortLC(m_slotNo, dstId, flco, ACTIVITY_VOICE);
|
||||
std::string src = m_lookup->find(srcId);
|
||||
std::string dst = m_lookup->find(dstId);
|
||||
std::string cn = m_lookup->findWithName(srcId);
|
||||
class CUserDBentry cn;
|
||||
m_lookup->findWithName(srcId, &cn);
|
||||
m_display->writeDMR(m_slotNo, cn, flco == FLCO_GROUP, dst, "N");
|
||||
|
||||
#if defined(DUMP_DMR)
|
||||
|
@ -1177,7 +1178,8 @@ void CDMRSlot::writeNetwork(const CDMRData& dmrData)
|
|||
setShortLC(m_slotNo, dstId, m_netLC->getFLCO(), ACTIVITY_VOICE);
|
||||
std::string src = m_lookup->find(srcId);
|
||||
std::string dst = m_lookup->find(dstId);
|
||||
std::string cn = m_lookup->findWithName(srcId);
|
||||
class CUserDBentry cn;
|
||||
m_lookup->findWithName(srcId, &cn);
|
||||
|
||||
m_display->writeDMR(m_slotNo, cn, m_netLC->getFLCO() == FLCO_GROUP, dst, "N");
|
||||
|
||||
|
@ -1373,7 +1375,8 @@ void CDMRSlot::writeNetwork(const CDMRData& dmrData)
|
|||
|
||||
std::string src = m_lookup->find(srcId);
|
||||
std::string dst = m_lookup->find(dstId);
|
||||
std::string cn = m_lookup->findWithName(srcId);
|
||||
class CUserDBentry cn;
|
||||
m_lookup->findWithName(srcId, &cn);
|
||||
|
||||
m_display->writeDMR(m_slotNo, cn, m_netLC->getFLCO() == FLCO_GROUP, dst, "N");
|
||||
|
||||
|
|
55
Display.cpp
55
Display.cpp
|
@ -151,6 +151,29 @@ void CDisplay::writeDMR(unsigned int slotNo, const std::string& src, bool group,
|
|||
writeDMRInt(slotNo, src, group, dst, type);
|
||||
}
|
||||
|
||||
void CDisplay::writeDMR(unsigned int slotNo, const class CUserDBentry& src, bool group, const std::string& dst, const char* type)
|
||||
{
|
||||
assert(type != NULL);
|
||||
|
||||
if (slotNo == 1U) {
|
||||
m_timer1.start();
|
||||
m_mode1 = MODE_IDLE;
|
||||
} else {
|
||||
m_timer2.start();
|
||||
m_mode2 = MODE_IDLE;
|
||||
}
|
||||
|
||||
if (int err = writeDMRIntEx(slotNo, src, group, dst, type)) {
|
||||
std::string src_str = src.get(keyCALLSIGN);
|
||||
if (err < 0 && !src.get(keyFIRST_NAME).empty()) {
|
||||
// emulate the result of old CDMRLookup::findWithName()
|
||||
// (it returned callsign and firstname)
|
||||
src_str += " " + src.get(keyFIRST_NAME);
|
||||
}
|
||||
writeDMRInt(slotNo, src_str, group, dst, type);
|
||||
}
|
||||
}
|
||||
|
||||
void CDisplay::writeDMRRSSI(unsigned int slotNo, unsigned char rssi)
|
||||
{
|
||||
if (rssi != 0U)
|
||||
|
@ -267,6 +290,17 @@ void CDisplay::writeNXDN(const char* source, bool group, unsigned int dest, cons
|
|||
writeNXDNInt(source, group, dest, type);
|
||||
}
|
||||
|
||||
void CDisplay::writeNXDN(const class CUserDBentry& source, bool group, unsigned int dest, const char* type)
|
||||
{
|
||||
assert(type != NULL);
|
||||
|
||||
m_timer1.start();
|
||||
m_mode1 = MODE_IDLE;
|
||||
|
||||
if (writeNXDNIntEx(source, group, dest, type))
|
||||
writeNXDNInt(source.get(keyCALLSIGN).c_str(), group, dest, type);
|
||||
}
|
||||
|
||||
void CDisplay::writeNXDNRSSI(unsigned char rssi)
|
||||
{
|
||||
if (rssi != 0U)
|
||||
|
@ -386,6 +420,20 @@ void CDisplay::writeDStarBERInt(float ber)
|
|||
{
|
||||
}
|
||||
|
||||
int CDisplay::writeDMRIntEx(unsigned int slotNo, const class CUserDBentry& src, bool group, const std::string& dst, const char* type)
|
||||
{
|
||||
/*
|
||||
* return value:
|
||||
* < 0 error condition (i.e. not supported)
|
||||
* -> call writeXXXXInt() to display
|
||||
* = 0 no error, writeXXXXIntEx() displayed whole status
|
||||
* = 1 no error, writeXXXXIntEx() displayed partial status
|
||||
* -> call writeXXXXInt() to display remain part
|
||||
* > 1 reserved for future use
|
||||
*/
|
||||
return -1; // not supported
|
||||
}
|
||||
|
||||
void CDisplay::writeDMRRSSIInt(unsigned int slotNo, unsigned char rssi)
|
||||
{
|
||||
}
|
||||
|
@ -421,6 +469,13 @@ void CDisplay::writeNXDNRSSIInt(unsigned char rssi)
|
|||
void CDisplay::writeNXDNBERInt(float ber)
|
||||
{
|
||||
}
|
||||
|
||||
int CDisplay::writeNXDNIntEx(const class CUserDBentry& source, bool group, unsigned int dest, const char* type)
|
||||
{
|
||||
/* return value definition is same as writeDMRIntEx() */
|
||||
return -1; // not supported
|
||||
}
|
||||
|
||||
|
||||
/* Factory method extracted from MMDVMHost.cpp - BG5HHP */
|
||||
CDisplay* CDisplay::createDisplay(const CConf& conf, CUMP* ump, CModem* modem)
|
||||
|
|
|
@ -20,6 +20,7 @@
|
|||
#define DISPLAY_H
|
||||
|
||||
#include "Timer.h"
|
||||
#include "UserDBentry.h"
|
||||
|
||||
#include <string>
|
||||
|
||||
|
@ -48,6 +49,7 @@ public:
|
|||
void clearDStar();
|
||||
|
||||
void writeDMR(unsigned int slotNo, const std::string& src, bool group, const std::string& dst, const char* type);
|
||||
void writeDMR(unsigned int slotNo, const class CUserDBentry& src, bool group, const std::string& dst, const char* type);
|
||||
void writeDMRRSSI(unsigned int slotNo, unsigned char rssi);
|
||||
void writeDMRBER(unsigned int slotNo, float ber);
|
||||
void writeDMRTA(unsigned int slotNo, unsigned char* talkerAlias, const char* type);
|
||||
|
@ -64,6 +66,7 @@ public:
|
|||
void clearP25();
|
||||
|
||||
void writeNXDN(const char* source, bool group, unsigned int dest, const char* type);
|
||||
void writeNXDN(const class CUserDBentry& source, bool group, unsigned int dest, const char* type);
|
||||
void writeNXDNRSSI(unsigned char rssi);
|
||||
void writeNXDNBER(float ber);
|
||||
void clearNXDN();
|
||||
|
@ -91,6 +94,7 @@ protected:
|
|||
virtual void clearDStarInt() = 0;
|
||||
|
||||
virtual void writeDMRInt(unsigned int slotNo, const std::string& src, bool group, const std::string& dst, const char* type) = 0;
|
||||
virtual int writeDMRIntEx(unsigned int slotNo, const class CUserDBentry& src, bool group, const std::string& dst, const char* type);
|
||||
virtual void writeDMRRSSIInt(unsigned int slotNo, unsigned char rssi);
|
||||
virtual void writeDMRTAInt(unsigned int slotNo, unsigned char* talkerAlias, const char* type);
|
||||
virtual void writeDMRBERInt(unsigned int slotNo, float ber);
|
||||
|
@ -107,6 +111,7 @@ protected:
|
|||
virtual void clearP25Int() = 0;
|
||||
|
||||
virtual void writeNXDNInt(const char* source, bool group, unsigned int dest, const char* type) = 0;
|
||||
virtual int writeNXDNIntEx(const class CUserDBentry& source, bool group, unsigned int dest, const char* type);
|
||||
virtual void writeNXDNRSSIInt(unsigned char rssi);
|
||||
virtual void writeNXDNBERInt(float ber);
|
||||
virtual void clearNXDNInt() = 0;
|
||||
|
|
2
Makefile
2
Makefile
|
@ -13,7 +13,7 @@ OBJECTS = \
|
|||
NetworkInfo.o Nextion.o NullDisplay.o NullModem.o NXDNAudio.o NXDNControl.o NXDNConvolution.o NXDNCRC.o NXDNFACCH1.o NXDNLayer3.o NXDNLICH.o \
|
||||
NXDNLookup.o NXDNNetwork.o NXDNSACCH.o NXDNUDCH.o P25Audio.o P25Control.o P25Data.o P25LowSpeedData.o P25Network.o P25NID.o P25Trellis.o P25Utils.o \
|
||||
POCSAGControl.o POCSAGNetwork.o QR1676.o RemoteControl.o RS129.o RS241213.o RSSIInterpolator.o SerialController.o SerialPort.o SHA256.o StopWatch.o Sync.o TFTSerial.o \
|
||||
TFTSurenoo.o Thread.o Timer.o UDPSocket.o UMP.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
TFTSurenoo.o Thread.o Timer.o UDPSocket.o UMP.o UserDB.o UserDBentry.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
|
||||
all: MMDVMHost RemoteCommand
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@ OBJECTS = \
|
|||
NetworkInfo.o Nextion.o NullDisplay.o NullModem.o NXDNAudio.o NXDNControl.o NXDNConvolution.o NXDNCRC.o NXDNFACCH1.o NXDNLayer3.o NXDNLICH.o NXDNLookup.o \
|
||||
NXDNNetwork.o NXDNSACCH.o NXDNUDCH.o P25Audio.o P25Control.o P25Data.o P25LowSpeedData.o P25Network.o P25NID.o P25Trellis.o P25Utils.o POCSAGControl.o \
|
||||
POCSAGNetwork.o QR1676.o RemoteControl.o RS129.o RS241213.o RSSIInterpolator.o SerialController.o SerialPort.o SHA256.o StopWatch.o Sync.o TFTSerial.o TFTSurenoo.o Thread.o Timer.o \
|
||||
UDPSocket.o UMP.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
UDPSocket.o UMP.o UserDB.o UserDBentry.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
|
||||
all: MMDVMHost RemoteCommand
|
||||
|
||||
|
|
|
@ -14,7 +14,7 @@ OBJECTS = \
|
|||
NetworkInfo.o Nextion.o NullDisplay.o NullModem.o NXDNAudio.o NXDNControl.o NXDNConvolution.o NXDNCRC.o NXDNFACCH1.o NXDNLayer3.o NXDNLICH.o NXDNLookup.o \
|
||||
NXDNNetwork.o NXDNSACCH.o NXDNUDCH.o P25Audio.o P25Control.o P25Data.o P25LowSpeedData.o P25Network.o P25NID.o P25Trellis.o P25Utils.o POCSAGControl.o \
|
||||
POCSAGNetwork.o QR1676.o RemoteControl.o RS129.o RS241213.o RSSIInterpolator.o SerialController.o SerialPort.o SHA256.o StopWatch.o Sync.o TFTSerial.o TFTSurenoo.o Thread.o \
|
||||
Timer.o UDPSocket.o UMP.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
Timer.o UDPSocket.o UMP.o UserDB.o UserDBentry.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
|
||||
all: MMDVMHost RemoteCommand
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@ OBJECTS = \
|
|||
NetworkInfo.o Nextion.o NullDisplay.o NullModem.o NXDNAudio.o NXDNControl.o NXDNConvolution.o NXDNCRC.o NXDNFACCH1.o NXDNLayer3.o NXDNLICH.o NXDNLookup.o \
|
||||
NXDNNetwork.o NXDNSACCH.o NXDNUDCH.o P25Audio.o P25Control.o P25Data.o P25LowSpeedData.o P25Network.o P25NID.o P25Trellis.o P25Utils.o POCSAGControl.o \
|
||||
POCSAGNetwork.o QR1676.o RemoteControl.o RS129.o RS241213.o RSSIInterpolator.o SerialController.o SerialPort.o SHA256.o StopWatch.o Sync.o TFTSerial.o TFTSurenoo.o Thread.o \
|
||||
Timer.o UDPSocket.o UMP.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
Timer.o UDPSocket.o UMP.o UserDB.o UserDBentry.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
|
||||
all: MMDVMHost RemoteCommand
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@ OBJECTS = \
|
|||
NetworkInfo.o Nextion.o NullDisplay.o NullModem.o NXDNAudio.o NXDNControl.o NXDNConvolution.o NXDNCRC.o NXDNFACCH1.o NXDNLayer3.o NXDNLICH.o NXDNLookup.o \
|
||||
NXDNNetwork.o NXDNSACCH.o NXDNUDCH.o P25Audio.o P25Control.o P25Data.o P25LowSpeedData.o P25Network.o P25NID.o P25Trellis.o P25Utils.o POCSAGControl.o \
|
||||
POCSAGNetwork.o QR1676.o RemoteControl.o RS129.o RS241213.o RSSIInterpolator.o SerialController.o SerialPort.o SHA256.o StopWatch.o Sync.o TFTSerial.o TFTSurenoo.o Thread.o \
|
||||
Timer.o UDPSocket.o UMP.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
Timer.o UDPSocket.o UMP.o UserDB.o UserDBentry.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
|
||||
all: MMDVMHost RemoteCommand
|
||||
|
||||
|
|
|
@ -14,7 +14,7 @@ OBJECTS = \
|
|||
NetworkInfo.o Nextion.o NullDisplay.o NullModem.o NXDNAudio.o NXDNControl.o NXDNConvolution.o NXDNCRC.o NXDNFACCH1.o NXDNLayer3.o NXDNLICH.o NXDNLookup.o \
|
||||
NXDNNetwork.o NXDNSACCH.o NXDNUDCH.o P25Audio.o P25Control.o P25Data.o P25LowSpeedData.o P25Network.o P25NID.o P25Trellis.o P25Utils.o POCSAGControl.o \
|
||||
POCSAGNetwork.o QR1676.o RemoteControl.o RS129.o RS241213.o RSSIInterpolator.o SerialController.o SerialPort.o SHA256.o StopWatch.o Sync.o TFTSerial.o TFTSurenoo.o Thread.o \
|
||||
Timer.o UDPSocket.o UMP.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
Timer.o UDPSocket.o UMP.o UserDB.o UserDBentry.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
|
||||
all: MMDVMHost RemoteCommand
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@ OBJECTS = \
|
|||
NullDisplay.o NullModem.o NXDNAudio.o NXDNControl.o NXDNConvolution.o NXDNCRC.o NXDNFACCH1.o NXDNLayer3.o NXDNLICH.o NXDNLookup.o NXDNNetwork.o \
|
||||
NXDNSACCH.o NXDNUDCH.o P25Audio.o P25Control.o P25Data.o P25LowSpeedData.o P25Network.o P25NID.o P25Trellis.o P25Utils.o POCSAGControl.o POCSAGNetwork.o \
|
||||
QR1676.o RemoteControl.o RS129.o RS241213.o RSSIInterpolator.o SerialController.o SerialPort.o SHA256.o StopWatch.o Sync.o TFTSerial.o TFTSurenoo.o Thread.o Timer.o UDPSocket.o \
|
||||
UMP.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
UMP.o UserDB.o UserDBebtry.o Utils.o YSFControl.o YSFConvolution.o YSFFICH.o YSFNetwork.o YSFPayload.o
|
||||
|
||||
all: MMDVMHost RemoteCommand
|
||||
|
||||
|
|
|
@ -835,15 +835,16 @@ void CNXDNControl::writeNetwork()
|
|||
|
||||
unsigned short dstId = m_netLayer3.getDestinationGroupId();
|
||||
bool grp = m_netLayer3.getIsGroup();
|
||||
std::string source = m_lookup->find(m_netLayer3.getSourceUnitId());
|
||||
class CUserDBentry source;
|
||||
m_lookup->findWithName(m_netLayer3.getSourceUnitId(), &source);
|
||||
|
||||
if (type == NXDN_MESSAGE_TYPE_TX_REL) {
|
||||
m_netFrames++;
|
||||
LogMessage("NXDN, received network end of transmission from %s to %s%u, %.1f seconds", source.c_str(), grp ? "TG " : "", dstId, float(m_netFrames) / 12.5F);
|
||||
LogMessage("NXDN, received network end of transmission from %s to %s%u, %.1f seconds", source.get(keyCALLSIGN).c_str(), grp ? "TG " : "", dstId, float(m_netFrames) / 12.5F);
|
||||
writeEndNet();
|
||||
} else if (type == NXDN_MESSAGE_TYPE_VCALL) {
|
||||
LogMessage("NXDN, received network transmission from %s to %s%u", source.c_str(), grp ? "TG " : "", dstId);
|
||||
m_display->writeNXDN(source.c_str(), grp, dstId, "N");
|
||||
LogMessage("NXDN, received network transmission from %s to %s%u", source.get(keyCALLSIGN).c_str(), grp ? "TG " : "", dstId);
|
||||
m_display->writeNXDN(source, grp, dstId, "N");
|
||||
|
||||
m_netTimeoutTimer.start();
|
||||
m_packetTimer.start();
|
||||
|
@ -892,9 +893,10 @@ void CNXDNControl::writeNetwork()
|
|||
unsigned short dstId = m_netLayer3.getDestinationGroupId();
|
||||
bool grp = m_netLayer3.getIsGroup();
|
||||
|
||||
std::string source = m_lookup->find(srcId);
|
||||
LogMessage("NXDN, received network transmission from %s to %s%u", source.c_str(), grp ? "TG " : "", dstId);
|
||||
m_display->writeNXDN(source.c_str(), grp, dstId, "N");
|
||||
class CUserDBentry source;
|
||||
m_lookup->findWithName(srcId, &source);
|
||||
LogMessage("NXDN, received network transmission from %s to %s%u", source.get(keyCALLSIGN).c_str(), grp ? "TG " : "", dstId);
|
||||
m_display->writeNXDN(source, grp, dstId, "N");
|
||||
|
||||
m_netTimeoutTimer.start();
|
||||
m_packetTimer.start();
|
||||
|
|
|
@ -30,7 +30,6 @@ CThread(),
|
|||
m_filename(filename),
|
||||
m_reloadTime(reloadTime),
|
||||
m_table(),
|
||||
m_mutex(),
|
||||
m_stop(false)
|
||||
{
|
||||
}
|
||||
|
@ -41,7 +40,7 @@ CNXDNLookup::~CNXDNLookup()
|
|||
|
||||
bool CNXDNLookup::read()
|
||||
{
|
||||
bool ret = load();
|
||||
bool ret = m_table.load(m_filename);
|
||||
|
||||
if (m_reloadTime > 0U)
|
||||
run();
|
||||
|
@ -61,7 +60,7 @@ void CNXDNLookup::entry()
|
|||
|
||||
timer.clock();
|
||||
if (timer.hasExpired()) {
|
||||
load();
|
||||
m_table.load(m_filename);
|
||||
timer.start();
|
||||
}
|
||||
}
|
||||
|
@ -81,6 +80,27 @@ void CNXDNLookup::stop()
|
|||
wait();
|
||||
}
|
||||
|
||||
void CNXDNLookup::findWithName(unsigned int id, class CUserDBentry *entry)
|
||||
{
|
||||
if (id == 0xFFFFU) {
|
||||
entry->clear();
|
||||
entry->set(keyCALLSIGN, "ALL");
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_table.lookup(id, entry)) {
|
||||
LogDebug("FindWithName =%s %s", entry->get(keyCALLSIGN).c_str(), entry->get(keyFIRST_NAME).c_str());
|
||||
} else {
|
||||
entry->clear();
|
||||
|
||||
char text[10U];
|
||||
::snprintf(text, sizeof(text), "%u", id);
|
||||
entry->set(keyCALLSIGN, text);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
std::string CNXDNLookup::find(unsigned int id)
|
||||
{
|
||||
std::string callsign;
|
||||
|
@ -88,73 +108,19 @@ std::string CNXDNLookup::find(unsigned int id)
|
|||
if (id == 0xFFFFU)
|
||||
return std::string("ALL");
|
||||
|
||||
m_mutex.lock();
|
||||
|
||||
try {
|
||||
callsign = m_table.at(id);
|
||||
} catch (...) {
|
||||
class CUserDBentry entry;
|
||||
if (m_table.lookup(id, &entry)) {
|
||||
callsign = entry.get(keyCALLSIGN);
|
||||
} else {
|
||||
char text[10U];
|
||||
::sprintf(text, "%u", id);
|
||||
::snprintf(text, sizeof(text), "%u", id);
|
||||
callsign = std::string(text);
|
||||
}
|
||||
|
||||
m_mutex.unlock();
|
||||
|
||||
return callsign;
|
||||
}
|
||||
|
||||
bool CNXDNLookup::exists(unsigned int id)
|
||||
{
|
||||
m_mutex.lock();
|
||||
|
||||
bool found = m_table.count(id) == 1U;
|
||||
|
||||
m_mutex.unlock();
|
||||
|
||||
return found;
|
||||
return m_table.lookup(id, NULL);
|
||||
}
|
||||
|
||||
bool CNXDNLookup::load()
|
||||
{
|
||||
FILE* fp = ::fopen(m_filename.c_str(), "rt");
|
||||
if (fp == NULL) {
|
||||
LogWarning("Cannot open the NXDN Id lookup file - %s", m_filename.c_str());
|
||||
return false;
|
||||
}
|
||||
|
||||
m_mutex.lock();
|
||||
|
||||
// Remove the old entries
|
||||
m_table.clear();
|
||||
|
||||
char buffer[100U];
|
||||
while (::fgets(buffer, 100U, fp) != NULL) {
|
||||
if (buffer[0U] == '#')
|
||||
continue;
|
||||
|
||||
char* p1 = ::strtok(buffer, ",\t\r\n");
|
||||
char* p2 = ::strtok(NULL, ",\t\r\n");
|
||||
|
||||
if (p1 != NULL && p2 != NULL) {
|
||||
unsigned int id = (unsigned int)::atoi(p1);
|
||||
if (id > 0U) {
|
||||
for (char* p = p2; *p != 0x00U; p++)
|
||||
*p = ::toupper(*p);
|
||||
|
||||
m_table[id] = std::string(p2);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
m_mutex.unlock();
|
||||
|
||||
::fclose(fp);
|
||||
|
||||
size_t size = m_table.size();
|
||||
if (size == 0U)
|
||||
return false;
|
||||
|
||||
LogInfo("Loaded %u Ids to the NXDN callsign lookup table", size);
|
||||
|
||||
return true;
|
||||
}
|
15
NXDNLookup.h
15
NXDNLookup.h
|
@ -20,10 +20,9 @@
|
|||
#define NXDNLookup_H
|
||||
|
||||
#include "Thread.h"
|
||||
#include "Mutex.h"
|
||||
#include "UserDB.h"
|
||||
|
||||
#include <string>
|
||||
#include <unordered_map>
|
||||
|
||||
class CNXDNLookup : public CThread {
|
||||
public:
|
||||
|
@ -35,19 +34,17 @@ public:
|
|||
virtual void entry();
|
||||
|
||||
std::string find(unsigned int id);
|
||||
void findWithName(unsigned int id, class CUserDBentry *entry);
|
||||
|
||||
bool exists(unsigned int id);
|
||||
|
||||
void stop();
|
||||
|
||||
private:
|
||||
std::string m_filename;
|
||||
unsigned int m_reloadTime;
|
||||
std::unordered_map<unsigned int, std::string> m_table;
|
||||
CMutex m_mutex;
|
||||
bool m_stop;
|
||||
|
||||
bool load();
|
||||
std::string m_filename;
|
||||
unsigned int m_reloadTime;
|
||||
class CUserDB m_table;
|
||||
bool m_stop;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -135,7 +135,7 @@ void CTFTSurenoo::setIdleInt()
|
|||
{
|
||||
setModeLine(STR_MMDVM);
|
||||
|
||||
::snprintf(m_temp, sizeof(m_temp), "%-6s / %u", m_callsign.c_str(), m_dmrid);
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s / %u", m_callsign.c_str(), m_dmrid);
|
||||
setStatusLine(statusLineNo(0), m_temp);
|
||||
setStatusLine(statusLineNo(1), "IDLE");
|
||||
|
||||
|
@ -184,14 +184,14 @@ void CTFTSurenoo::writeDStarInt(const char* my1, const char* my2, const char* yo
|
|||
|
||||
setModeLine(STR_MMDVM);
|
||||
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s %.8s/%4.4s", type, my1, my2);
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s %s/%s", type, my1, my2);
|
||||
setStatusLine(statusLineNo(0), m_temp);
|
||||
|
||||
::snprintf(m_temp, sizeof(m_temp), "%.8s", your);
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s", your);
|
||||
setStatusLine(statusLineNo(1), m_temp);
|
||||
|
||||
if (::strcmp(reflector, " ") != 0)
|
||||
::snprintf(m_temp, sizeof(m_temp), "via %.8s", reflector);
|
||||
::snprintf(m_temp, sizeof(m_temp), "via %s", reflector);
|
||||
else
|
||||
::strcpy(m_temp, "");
|
||||
setStatusLine(statusLineNo(2), m_temp);
|
||||
|
@ -202,8 +202,8 @@ void CTFTSurenoo::writeDStarInt(const char* my1, const char* my2, const char* yo
|
|||
void CTFTSurenoo::clearDStarInt()
|
||||
{
|
||||
setStatusLine(statusLineNo(0), "Listening");
|
||||
setStatusLine(statusLineNo(1), "");
|
||||
setStatusLine(statusLineNo(2), "");
|
||||
for (int i = 1; i < STATUS_LINES; i++)
|
||||
setStatusLine(statusLineNo(i), "");
|
||||
}
|
||||
|
||||
void CTFTSurenoo::writeDMRInt(unsigned int slotNo, const std::string& src, bool group, const std::string& dst, const char* type)
|
||||
|
@ -230,6 +230,25 @@ void CTFTSurenoo::writeDMRInt(unsigned int slotNo, const std::string& src, bool
|
|||
m_mode = MODE_DMR;
|
||||
}
|
||||
|
||||
int CTFTSurenoo::writeDMRIntEx(unsigned int slotNo, const class CUserDBentry& src, bool group, const std::string& dst, const char* type)
|
||||
{
|
||||
assert(type != NULL);
|
||||
|
||||
// duplex mode is not supported
|
||||
if (m_duplex)
|
||||
return -1;
|
||||
|
||||
setModeLine(STR_DMR);
|
||||
setStatusLine(statusLineNo(2), (src.get(keyFIRST_NAME) + " " + src.get(keyLAST_NAME)).c_str());
|
||||
setStatusLine(statusLineNo(3), src.get(keyCITY).c_str());
|
||||
setStatusLine(statusLineNo(4), src.get(keySTATE).c_str());
|
||||
setStatusLine(statusLineNo(5), src.get(keyCOUNTRY).c_str());
|
||||
|
||||
m_mode = MODE_DMR;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
void CTFTSurenoo::clearDMRInt(unsigned int slotNo)
|
||||
{
|
||||
int pos = m_duplex ? (slotNo - 1) : 0;
|
||||
|
@ -239,7 +258,8 @@ void CTFTSurenoo::clearDMRInt(unsigned int slotNo)
|
|||
::snprintf(m_temp, sizeof(m_temp), "TS%d", slotNo);
|
||||
setStatusLine(statusLineNo(pos * 2 + 1), m_temp);
|
||||
} else {
|
||||
setStatusLine(statusLineNo(1), "");
|
||||
for (int i = 1; i < STATUS_LINES; i++)
|
||||
setStatusLine(statusLineNo(i), "");
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -252,14 +272,14 @@ void CTFTSurenoo::writeFusionInt(const char* source, const char* dest, const cha
|
|||
|
||||
setModeLine(STR_YSF);
|
||||
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s %.10s", type, source);
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s %s", type, source);
|
||||
setStatusLine(statusLineNo(0), m_temp);
|
||||
|
||||
::snprintf(m_temp, sizeof(m_temp), " %.10s", dest);
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s", dest);
|
||||
setStatusLine(statusLineNo(1), m_temp);
|
||||
|
||||
if (::strcmp(origin, " ") != 0)
|
||||
::snprintf(m_temp, sizeof(m_temp), "at %.10s", origin);
|
||||
::snprintf(m_temp, sizeof(m_temp), "at %s", origin);
|
||||
else
|
||||
::strcpy(m_temp, "");
|
||||
setStatusLine(statusLineNo(2), m_temp);
|
||||
|
@ -279,10 +299,10 @@ void CTFTSurenoo::writeP25Int(const char* source, bool group, unsigned int dest,
|
|||
|
||||
setModeLine(STR_P25);
|
||||
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s %.10s", type, source);
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s %s", type, source);
|
||||
setStatusLine(statusLineNo(0), m_temp);
|
||||
|
||||
::snprintf(m_temp, sizeof(m_temp), " %s%u", group ? "TG" : "", dest);
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s%u", group ? "TG" : "", dest);
|
||||
setStatusLine(statusLineNo(1), m_temp);
|
||||
|
||||
m_mode = MODE_P25;
|
||||
|
@ -298,17 +318,33 @@ void CTFTSurenoo::writeNXDNInt(const char* source, bool group, unsigned int dest
|
|||
assert(source != NULL);
|
||||
assert(type != NULL);
|
||||
|
||||
setModeLine(STR_NXDN);
|
||||
if (m_mode != MODE_NXDN)
|
||||
setModeLine(STR_NXDN);
|
||||
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s %.10s", type, source);
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s %s", type, source);
|
||||
setStatusLine(statusLineNo(0), m_temp);
|
||||
|
||||
::snprintf(m_temp, sizeof(m_temp), " %s%u", group ? "TG" : "", dest);
|
||||
::snprintf(m_temp, sizeof(m_temp), "%s%u", group ? "TG" : "", dest);
|
||||
setStatusLine(statusLineNo(1), m_temp);
|
||||
|
||||
m_mode = MODE_NXDN;
|
||||
}
|
||||
|
||||
int CTFTSurenoo::writeNXDNIntEx(const class CUserDBentry& source, bool group, unsigned int dest, const char* type)
|
||||
{
|
||||
assert(type != NULL);
|
||||
|
||||
setModeLine(STR_NXDN);
|
||||
setStatusLine(statusLineNo(2), (source.get(keyFIRST_NAME) + " " + source.get(keyLAST_NAME)).c_str());
|
||||
setStatusLine(statusLineNo(3), source.get(keyCITY).c_str());
|
||||
setStatusLine(statusLineNo(4), source.get(keySTATE).c_str());
|
||||
setStatusLine(statusLineNo(5), source.get(keyCOUNTRY).c_str());
|
||||
|
||||
m_mode = MODE_NXDN;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
void CTFTSurenoo::clearNXDNInt()
|
||||
{
|
||||
clearDStarInt();
|
||||
|
|
|
@ -23,6 +23,7 @@
|
|||
#include "Display.h"
|
||||
#include "Defines.h"
|
||||
#include "SerialPort.h"
|
||||
#include "UserDBentry.h"
|
||||
|
||||
#include <string>
|
||||
|
||||
|
@ -46,6 +47,7 @@ protected:
|
|||
virtual void clearDStarInt();
|
||||
|
||||
virtual void writeDMRInt(unsigned int slotNo, const std::string& src, bool group, const std::string& dst, const char* type);
|
||||
virtual int writeDMRIntEx(unsigned int slotNo, const class CUserDBentry& src, bool group, const std::string& dst, const char* type);
|
||||
virtual void clearDMRInt(unsigned int slotNo);
|
||||
|
||||
virtual void writeFusionInt(const char* source, const char* dest, const char* type, const char* origin);
|
||||
|
@ -55,6 +57,7 @@ protected:
|
|||
virtual void clearP25Int();
|
||||
|
||||
virtual void writeNXDNInt(const char* source, bool group, unsigned int dest, const char* type);
|
||||
virtual int writeNXDNIntEx(const class CUserDBentry& source, bool group, unsigned int dest, const char* type);
|
||||
virtual void clearNXDNInt();
|
||||
|
||||
virtual void writePOCSAGInt(uint32_t ric, const std::string& message);
|
||||
|
|
187
UserDB.cpp
Normal file
187
UserDB.cpp
Normal file
|
@ -0,0 +1,187 @@
|
|||
/*
|
||||
* Copyright (C) 2020 by SASANO Takayoshi JG1UAA
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*/
|
||||
#include "UserDB.h"
|
||||
#include "Log.h"
|
||||
|
||||
#include <cstdio>
|
||||
#include <cstring>
|
||||
#include <cctype>
|
||||
|
||||
CUserDB::CUserDB() :
|
||||
m_table(),
|
||||
m_mutex()
|
||||
{
|
||||
}
|
||||
|
||||
CUserDB::~CUserDB()
|
||||
{
|
||||
}
|
||||
|
||||
bool CUserDB::lookup(unsigned int id, class CUserDBentry *entry)
|
||||
{
|
||||
bool rv;
|
||||
|
||||
m_mutex.lock();
|
||||
|
||||
try {
|
||||
if (entry != NULL)
|
||||
*entry = m_table.at(id);
|
||||
else
|
||||
m_table.at(id);
|
||||
|
||||
rv = true;
|
||||
} catch (...) {
|
||||
rv = false;
|
||||
}
|
||||
|
||||
m_mutex.unlock();
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
bool CUserDB::load(std::string const& filename)
|
||||
{
|
||||
FILE* fp = ::fopen(filename.c_str(), "r");
|
||||
if (fp == NULL) {
|
||||
LogWarning("Cannot open ID lookup file - %s", filename.c_str());
|
||||
return false;
|
||||
}
|
||||
|
||||
m_mutex.lock();
|
||||
|
||||
// Remove the old entries;
|
||||
m_table.clear();
|
||||
|
||||
// set index for entries
|
||||
char buffer[256U];
|
||||
if (::fgets(buffer, sizeof(buffer), fp) == NULL) {
|
||||
LogWarning("ID lookup file has no entry - %s", filename.c_str());
|
||||
m_mutex.unlock();
|
||||
::fclose(fp);
|
||||
return false;
|
||||
}
|
||||
|
||||
// no index - set default
|
||||
std::unordered_map<std::string, int> index;
|
||||
if (!makeindex(buffer, index)) {
|
||||
::strncpy(buffer, keyRADIO_ID "," keyCALLSIGN "," keyFIRST_NAME, sizeof(buffer));
|
||||
makeindex(buffer, index);
|
||||
::rewind(fp);
|
||||
}
|
||||
|
||||
while (::fgets(buffer, sizeof(buffer), fp) != NULL) {
|
||||
if (buffer[0U] != '#')
|
||||
parse(buffer, index);
|
||||
}
|
||||
|
||||
::fclose(fp);
|
||||
|
||||
size_t size = m_table.size();
|
||||
m_mutex.unlock();
|
||||
|
||||
LogInfo("Loaded %u IDs to lookup table - %s", size, filename.c_str());
|
||||
|
||||
return size != 0U;
|
||||
}
|
||||
|
||||
bool CUserDB::makeindex(char* buf, std::unordered_map<std::string, int>& index)
|
||||
{
|
||||
int i;
|
||||
char *p1, *p2;
|
||||
|
||||
// Remove the old index
|
||||
index.clear();
|
||||
|
||||
for (i = 0, p1 = tokenize(buf, &p2); p1 != NULL;
|
||||
i++, p1 = tokenize(p2, &p2)) {
|
||||
|
||||
// create [column keyword] - [column number] table
|
||||
if (CUserDBentry::isValidKey(p1))
|
||||
index[p1] = i;
|
||||
}
|
||||
|
||||
try {
|
||||
index.at(keyRADIO_ID);
|
||||
index.at(keyCALLSIGN);
|
||||
return true;
|
||||
} catch (...) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
void CUserDB::parse(char* buf, std::unordered_map<std::string, int>& index)
|
||||
{
|
||||
int i;
|
||||
char *p1, *p2;
|
||||
std::unordered_map<std::string, char*> ptr;
|
||||
unsigned int id;
|
||||
|
||||
for (i = 0, p1 = tokenize(buf, &p2); p1 != NULL;
|
||||
i++, p1 = tokenize(p2, &p2)) {
|
||||
|
||||
for (auto it = index.begin(); it != index.end(); it++) {
|
||||
// first: column keyword, second: column number
|
||||
if (it->second == i) {
|
||||
ptr[it->first] = p1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
try {
|
||||
ptr.at(keyRADIO_ID);
|
||||
ptr.at(keyCALLSIGN);
|
||||
} catch (...) {
|
||||
return;
|
||||
}
|
||||
|
||||
id = (unsigned int)::atoi(ptr[keyRADIO_ID]);
|
||||
toupper_string(ptr[keyCALLSIGN]);
|
||||
|
||||
for (auto it = ptr.begin(); it != ptr.end(); it++) {
|
||||
// no need to regist radio ID
|
||||
if (it->first == keyRADIO_ID)
|
||||
continue;
|
||||
|
||||
m_table[id].set(it->first, it->second);
|
||||
}
|
||||
}
|
||||
|
||||
void CUserDB::toupper_string(char* str)
|
||||
{
|
||||
while (*str != '\0') {
|
||||
*str = ::toupper(*str);
|
||||
str++;
|
||||
}
|
||||
}
|
||||
|
||||
char* CUserDB::tokenize(char* str, char** next)
|
||||
{
|
||||
if (*str == '\0')
|
||||
return NULL;
|
||||
|
||||
char* p = ::strpbrk(str, ",\t\r\n");
|
||||
if (p == NULL) {
|
||||
*next = str + ::strlen(str);
|
||||
} else {
|
||||
*p = '\0';
|
||||
*next = p + 1;
|
||||
}
|
||||
|
||||
return str;
|
||||
}
|
43
UserDB.h
Normal file
43
UserDB.h
Normal file
|
@ -0,0 +1,43 @@
|
|||
/*
|
||||
* Copyright (C) 2020 by SASANO Takayoshi JG1UAA
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*/
|
||||
|
||||
#if !defined(USERDB_H)
|
||||
#define USERDB_H
|
||||
|
||||
#include "UserDBentry.h"
|
||||
#include "Mutex.h"
|
||||
|
||||
class CUserDB {
|
||||
public:
|
||||
CUserDB();
|
||||
~CUserDB();
|
||||
|
||||
bool lookup(unsigned int id, class CUserDBentry *entry);
|
||||
bool load(std::string const& filename);
|
||||
|
||||
private:
|
||||
bool makeindex(char* buf, std::unordered_map<std::string, int>& index);
|
||||
void parse(char* buf, std::unordered_map<std::string, int>& index);
|
||||
void toupper_string(char* str);
|
||||
char* tokenize(char* str, char** next);
|
||||
|
||||
std::unordered_map<unsigned int, class CUserDBentry> m_table;
|
||||
CMutex m_mutex;
|
||||
};
|
||||
|
||||
#endif
|
59
UserDBentry.cpp
Normal file
59
UserDBentry.cpp
Normal file
|
@ -0,0 +1,59 @@
|
|||
/*
|
||||
* Copyright (C) 2020 by SASANO Takayoshi JG1UAA
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*/
|
||||
#include "UserDBentry.h"
|
||||
#include <algorithm>
|
||||
|
||||
CUserDBentry::CUserDBentry() :
|
||||
m_db()
|
||||
{
|
||||
}
|
||||
|
||||
CUserDBentry::~CUserDBentry()
|
||||
{
|
||||
}
|
||||
|
||||
const std::vector<std::string> CUserDBentry::keyList {
|
||||
keyRADIO_ID, keyCALLSIGN, keyFIRST_NAME, keyLAST_NAME,
|
||||
keyCITY, keySTATE, keyCOUNTRY,
|
||||
};
|
||||
|
||||
bool CUserDBentry::isValidKey(const std::string key)
|
||||
{
|
||||
auto it = std::find(keyList.begin(), keyList.end(), key);
|
||||
return it != keyList.end();
|
||||
}
|
||||
|
||||
void CUserDBentry::set(const std::string key, const std::string value)
|
||||
{
|
||||
if (!value.empty() && isValidKey(key))
|
||||
m_db[key] = value;
|
||||
}
|
||||
|
||||
const std::string CUserDBentry::get(const std::string key) const
|
||||
{
|
||||
try {
|
||||
return m_db.at(key);
|
||||
} catch (...) {
|
||||
return "";
|
||||
}
|
||||
}
|
||||
|
||||
void CUserDBentry::clear(void)
|
||||
{
|
||||
m_db.clear();
|
||||
}
|
50
UserDBentry.h
Normal file
50
UserDBentry.h
Normal file
|
@ -0,0 +1,50 @@
|
|||
/*
|
||||
* Copyright (C) 2020 by SASANO Takayoshi JG1UAA
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*/
|
||||
|
||||
#if !defined(USERDBENTRY_H)
|
||||
#define USERDBENTRY_H
|
||||
|
||||
#include <string>
|
||||
#include <unordered_map>
|
||||
#include <vector>
|
||||
|
||||
#define keyRADIO_ID "RADIO_ID"
|
||||
#define keyCALLSIGN "CALLSIGN"
|
||||
#define keyFIRST_NAME "FIRST_NAME"
|
||||
#define keyLAST_NAME "LAST_NAME"
|
||||
#define keyCITY "CITY"
|
||||
#define keySTATE "STATE"
|
||||
#define keyCOUNTRY "COUNTRY"
|
||||
|
||||
class CUserDBentry {
|
||||
public:
|
||||
CUserDBentry();
|
||||
~CUserDBentry();
|
||||
|
||||
static const std::vector<std::string> keyList;
|
||||
static bool isValidKey(const std::string key);
|
||||
|
||||
void set(const std::string key, const std::string value);
|
||||
const std::string get(const std::string key) const;
|
||||
void clear(void);
|
||||
|
||||
private:
|
||||
std::unordered_map<std::string, std::string> m_db;
|
||||
};
|
||||
|
||||
#endif
|
Loading…
Reference in a new issue