From 565a6c70b98a477cda387aa27d3ae9ed038f7360 Mon Sep 17 00:00:00 2001 From: f4exb Date: Fri, 24 Jul 2020 08:00:23 +0200 Subject: [PATCH] NXDN: tolerate 1 symbol error on sync sequences --- dsd_decoder.cpp | 16 ++++++++++++---- dsd_decoder.h | 1 + 2 files changed, 13 insertions(+), 4 deletions(-) diff --git a/dsd_decoder.cpp b/dsd_decoder.cpp index b773d0b..524a4c1 100644 --- a/dsd_decoder.cpp +++ b/dsd_decoder.cpp @@ -16,6 +16,7 @@ #include #include +#include #include "timeutil.h" #include "dsd_decoder.h" @@ -666,6 +667,7 @@ int DSDDecoder::getFrameSync() else // Sync identification starts here { m_dmrBurstType = DSDDMR::DSDDMRBurstNone; + unsigned char tmp[64]; if (m_opts.frame_p25p1 == 1) { @@ -922,7 +924,7 @@ int DSDDecoder::getFrameSync() } if ((m_opts.frame_nxdn96 == 1) || (m_opts.frame_nxdn48 == 1)) { - if (memcmp(m_dsdSymbol.getSyncDibitBack(19), m_syncNXDNRDCHFull, 19) == 0) // long sync (with preamble) + if (countDiff(m_dsdSymbol.getSyncDibitBack(19), m_syncNXDNRDCHFull, tmp, 19) <= 1) // long sync (with preamble) { m_nxdnInterSyncCount = 0; m_state.carrier = 1; @@ -951,7 +953,7 @@ int DSDDecoder::getFrameSync() m_mbeRate = DSDMBERate3600x2450; return (int) DSDSyncNXDNP; // done } - else if (memcmp(m_dsdSymbol.getSyncDibitBack(19), m_syncNXDNRDCHFullInv, 19) == 0) // long sync (with preamble) inverted + else if (countDiff(m_dsdSymbol.getSyncDibitBack(19), m_syncNXDNRDCHFullInv, tmp, 19) <= 1) // long sync (with preamble) inverted { m_nxdnInterSyncCount = 0; m_state.carrier = 1; @@ -980,7 +982,7 @@ int DSDDecoder::getFrameSync() m_mbeRate = DSDMBERate3600x2450; return (int) DSDSyncNXDNN; // done } - else if (memcmp(m_dsdSymbol.getSyncDibitBack(10), m_syncNXDNRDCHFSW, 10) == 0) // short sync + else if (countDiff(m_dsdSymbol.getSyncDibitBack(10), m_syncNXDNRDCHFSW, tmp, 10) <= 1) // short sync { if ((m_nxdnInterSyncCount > 0) && (m_nxdnInterSyncCount % 192 == 0)) { @@ -1014,7 +1016,7 @@ int DSDDecoder::getFrameSync() m_nxdnInterSyncCount = 0; } } - else if (memcmp(m_dsdSymbol.getSyncDibitBack(10), m_syncNXDNRDCHFSWInv, 10) == 0) // short sync inverted + else if (countDiff(m_dsdSymbol.getSyncDibitBack(10), m_syncNXDNRDCHFSWInv, tmp, 10) <= 1) // short sync inverted { if ((m_nxdnInterSyncCount > 0) && (m_nxdnInterSyncCount % 192 == 0)) { @@ -1468,4 +1470,10 @@ int DSDDecoder::comp(const void *a, const void *b) return 1; } +int DSDDecoder::countDiff(const unsigned char *a, const unsigned char *b, unsigned char *t, unsigned int len) +{ + std::transform(a, a + len, b, t, std::bit_xor()); + return std::count_if(t, t + len, [](unsigned char& c) { return c != 0; }); +} + } // namespace dsdcc diff --git a/dsd_decoder.h b/dsd_decoder.h index 89173f0..88f2c4b 100644 --- a/dsd_decoder.h +++ b/dsd_decoder.h @@ -320,6 +320,7 @@ class DSDCC_API DSDDecoder void printFrameInfo(); void processFrameInit(); static int comp(const void *a, const void *b); + static int countDiff(const unsigned char *a, const unsigned char *b, unsigned char *t, unsigned int len); DSDOpts m_opts; DSDState m_state;