Beispiel #1
0
void CYSFRX::processNone(q15_t sample)
{
  m_symbolBuffer <<= 1;
  if (sample < 0)
    m_symbolBuffer |= 0x01U;

  m_symbols[m_symbolPtr] = sample;

  // Fuzzy matching of the data sync bit sequence
  if (countBits32((m_symbolBuffer & YSF_SYNC_SYMBOLS_MASK) ^ YSF_SYNC_SYMBOLS) <= SYNC_SYMBOL_ERRS) {
    q15_t max  = -16000;
    q15_t min  =  16000;

    for (uint8_t i = 0U; i < YSF_SYNC_LENGTH_SYMBOLS; i++) {
      q15_t val = m_symbols[i];
      if (val > max)
        max = val;
      if (val < min)
        min = val;
    }

    q15_t centre = (max + min) >> 1;

    q31_t v1 = (max - centre) * m_scale;
    q15_t threshold = q15_t(v1 >> 15);

    uint16_t ptr = m_symbolPtr + 1U;
    if (ptr >= YSF_SYNC_LENGTH_SYMBOLS)
      ptr = 0U;

    for (uint8_t i = 0U; i < YSF_SYNC_LENGTH_SYMBOLS; i++) {
      q15_t sample = m_symbols[ptr] - centre;

      if (sample < -threshold) {
        m_bitBuffer <<= 2;
        m_bitBuffer |= 0x01U;
      } else if (sample < 0) {
        m_bitBuffer <<= 2;
        m_bitBuffer |= 0x00U;
      } else if (sample < threshold) {
        m_bitBuffer <<= 2;
        m_bitBuffer |= 0x02U;
      } else {
        m_bitBuffer <<= 2;
        m_bitBuffer |= 0x03U;
      }

      ptr++;
      if (ptr >= YSF_SYNC_LENGTH_SYMBOLS)
        ptr = 0U;
    }

    // Fuzzy matching of the data sync bit sequence
    if (countBits64((m_bitBuffer & YSF_SYNC_BITS_MASK) ^ YSF_SYNC_BITS) <= SYNC_BIT_START_ERRS) {
      DEBUG5("YSFRX: sync found in None min/max/centre/threshold", min, max, centre, threshold);
      for (uint8_t i = 0U; i < YSF_SYNC_LENGTH_BYTES; i++)
        m_buffer[i] = YSF_SYNC_BYTES[i];
      m_centre    = centre;
      m_threshold = threshold;
      m_lostCount = MAX_SYNC_FRAMES;
      m_bufferPtr = YSF_SYNC_LENGTH_BITS;
      m_state     = YSFRXS_DATA;

      io.setDecode(true);
      io.setADCDetection(true);
    }
  }
Beispiel #2
0
void CDMRSlotRX::correlateSync(q15_t sample)
{
  m_bitBuffer[m_bitPtr] <<= 1;
  if (sample < 0)
    m_bitBuffer[m_bitPtr] |= 0x01U;

  uint8_t errs = countBits32((m_bitBuffer[m_bitPtr] & DMR_SYNC_SYMBOLS_MASK) ^ DMR_MS_DATA_SYNC_SYMBOLS);

  // The voice sync is the complement of the data sync
  bool data  = (errs <= MAX_SYNC_SYMBOLS_ERRS);
  bool voice = (errs >= (DMR_SYNC_LENGTH_SYMBOLS - MAX_SYNC_SYMBOLS_ERRS));

  if (data || voice) {
    uint16_t ptr = m_dataPtr - DMR_SYNC_LENGTH_SAMPLES + DMR_RADIO_SYMBOL_LENGTH;

    q31_t corr = 0;
    q15_t min =  16000;
    q15_t max = -16000;

    uint32_t mask = 0x00800000U;
    for (uint8_t i = 0U; i < DMR_SYNC_LENGTH_SYMBOLS; i++, mask >>= 1) {
      bool b = (DMR_MS_DATA_SYNC_SYMBOLS & mask) == mask;

      if (m_buffer[ptr] > max)
        max = m_buffer[ptr];
      if (m_buffer[ptr] < min)
        min = m_buffer[ptr];

      if (data)
        corr += b ? -m_buffer[ptr] : m_buffer[ptr];
      else  // if (voice)
        corr += b ? m_buffer[ptr] : -m_buffer[ptr];

      ptr += DMR_RADIO_SYMBOL_LENGTH;
    }

    if (corr > m_maxCorr) {
      q15_t centre = (max + min) >> 1;

      q31_t v1 = (max - centre) * SCALING_FACTOR;
      q15_t threshold = q15_t(v1 >> 15);

      uint8_t sync[DMR_SYNC_BYTES_LENGTH];
      uint16_t ptr = m_dataPtr - DMR_SYNC_LENGTH_SAMPLES + DMR_RADIO_SYMBOL_LENGTH;
      samplesToBits(ptr, DMR_SYNC_LENGTH_SYMBOLS, sync, 4U, centre, threshold);

      if (data) {
        uint8_t errs = 0U;
        for (uint8_t i = 0U; i < DMR_SYNC_BYTES_LENGTH; i++)
          errs += countBits8((sync[i] & DMR_SYNC_BYTES_MASK[i]) ^ DMR_MS_DATA_SYNC_BYTES[i]);

        if (errs <= MAX_SYNC_BYTES_ERRS) {
          DEBUG5("DMRSlotRX: data sync found slot/pos/centre/threshold", m_slot ? 2U : 1U, m_dataPtr, centre, threshold);
          m_maxCorr   = corr;
          m_centre    = centre;
          m_threshold = threshold;
          m_control   = 0x40U;
          m_endPtr    = m_dataPtr + DMR_SLOT_TYPE_LENGTH_SAMPLES / 2U + DMR_INFO_LENGTH_SAMPLES / 2U - 1U;
          DEBUG3("DMRSlotRX: slot/endPtr", m_slot ? 2U : 1U, m_endPtr);
        }
      } else {  // if (voice)
        uint8_t errs = 0U;
        for (uint8_t i = 0U; i < DMR_SYNC_BYTES_LENGTH; i++)
          errs += countBits8((sync[i] & DMR_SYNC_BYTES_MASK[i]) ^ DMR_MS_VOICE_SYNC_BYTES[i]);

        if (errs <= MAX_SYNC_BYTES_ERRS) {
          DEBUG5("DMRSlotRX: voice sync found slot/pos/centre/threshold", m_slot ? 2U : 1U, m_dataPtr, centre, threshold);
          m_maxCorr   = corr;
          m_centre    = centre;
          m_threshold = threshold;
          m_control   = 0x20U;
          m_endPtr    = m_dataPtr + DMR_SLOT_TYPE_LENGTH_SAMPLES / 2U + DMR_INFO_LENGTH_SAMPLES / 2U - 1U;
          DEBUG3("DMRSlotRX: slot/endPtr", m_slot ? 2U : 1U, m_endPtr);
        }
      }
    }