From 1f956f56bde94115e2cd6c384633efcc56150d73 Mon Sep 17 00:00:00 2001 From: csrichter Date: Tue, 2 May 2017 15:03:11 +0200 Subject: [PATCH] added calcSyndrome_vec from redsea, TODO: compare with "calc_syndrome" which is faster and if they have the same result --- lib/rds_decoder_redsea_impl.cc | 35 +++++++++++++++++++++++++++++----- 1 file changed, 30 insertions(+), 5 deletions(-) diff --git a/lib/rds_decoder_redsea_impl.cc b/lib/rds_decoder_redsea_impl.cc index e6d0179..384da0a 100644 --- a/lib/rds_decoder_redsea_impl.cc +++ b/lib/rds_decoder_redsea_impl.cc @@ -120,6 +120,30 @@ uint16_t rds_decoder_redsea_impl::calc_syndrome(uint32_t message,uint8_t mlen) { } //redsea stuff: +// Section B.1.1: '-- calculated by the modulo-two addition of all the rows of +// the -- matrix for which the corresponding coefficient in the -- vector is 1.' +uint32_t matrixMultiply(uint32_t vec, const std::vector& matrix) { + uint32_t result = 0; + + for (size_t k=0; k < matrix.size(); k++) + if ((vec >> k) & 0x01) + result ^= matrix[matrix.size() - 1 - k]; + + return result; +} + +// Section B.2.1: 'The calculation of the syndromes -- can easily be done by +// multiplying each word with the parity matrix H.' +uint32_t calcSyndrome_vec(uint32_t vec) { + static const std::vector parity_check_matrix({ + 0x200, 0x100, 0x080, 0x040, 0x020, 0x010, 0x008, 0x004, + 0x002, 0x001, 0x2dc, 0x16e, 0x0b7, 0x287, 0x39f, 0x313, + 0x355, 0x376, 0x1bb, 0x201, 0x3dc, + 0x1ee, 0x0f7, 0x2a7, 0x38f, 0x31b + }); + + return matrixMultiply(vec, parity_check_matrix); +} const unsigned kBitmask16 = 0x000FFFF; const unsigned kBitmask26 = 0x3FFFFFF; const unsigned kBitmask28 = 0xFFFFFFF; @@ -144,8 +168,8 @@ static const char * const offset_name[]={"A","B","C","D","c"};*/ for (uint32_t e : {0x1,0x3}) {//fix up to 2-bit burst errors (as book says) for (int shift=0; shift < 26; shift++) { uint32_t errvec = ((e << shift) & kBitmask26); - //uint16_t sy = calc_syndrome(errvec ^ offset_word[offset_num],26); uint32_t sy = calc_syndrome(errvec ^ offset_word[offset_num],26);//why uint32 and not uint16 as everywhere else??? + //uint32_t sy = calcSyndrome_vec(errvec ^ offset_word[offset_num]); result.insert({{sy, offset_name[offset_num]}, errvec}); //dout << "adding sy:"<(errvec) < 0) { - uint32_t err = kErrorLookup.at({(uint16_t)syndrome, (char)offset}); + if (kErrorLookup.count({syndrome, offset}) > 0) { + uint32_t err = kErrorLookup.at({syndrome, offset}); //dout << "correcting"<