mirror of https://github.com/g4klx/MMDVM.git
Merge pull request #136 from juribeparada/master
Adding DMR 1031 Hz Test Pattern
This commit is contained in:
commit
94e65ba6cc
117
CalDMR.cpp
117
CalDMR.cpp
|
@ -21,19 +21,121 @@
|
|||
#include "Globals.h"
|
||||
#include "CalDMR.h"
|
||||
|
||||
// Voice LC Header, CC: 1, srcID: 1, dstID: TG9
|
||||
const uint8_t VH_1K[] = {0x00U,
|
||||
0x00U, 0x20U, 0x08U, 0x08U, 0x02U, 0x38U, 0x15U, 0x00U, 0x2CU, 0xA0U, 0x14U,
|
||||
0x60U, 0x84U, 0x6DU, 0xFFU, 0x57U, 0xD7U, 0x5DU, 0xF5U, 0xDEU, 0x30U, 0x30U,
|
||||
0x01U, 0x10U, 0x01U, 0x40U, 0x03U, 0xC0U, 0x13U, 0xC1U, 0x1EU, 0x80U, 0x6FU};
|
||||
|
||||
// Voice Term with LC, CC: 1, srcID: 1, dstID: TG9
|
||||
const uint8_t VT_1K[] = {0x00U,
|
||||
0x00U, 0x4FU, 0x08U, 0xDCU, 0x02U, 0x88U, 0x15U, 0x78U, 0x2CU, 0xD0U, 0x14U,
|
||||
0xC0U, 0x84U, 0xADU, 0xFFU, 0x57U, 0xD7U, 0x5DU, 0xF5U, 0xD9U, 0x65U, 0x24U,
|
||||
0x02U, 0x28U, 0x06U, 0x20U, 0x0FU, 0x80U, 0x1BU, 0xC1U, 0x07U, 0x80U, 0x5CU};
|
||||
|
||||
// Voice coding data + FEC, 1031 Hz Test Pattern
|
||||
const uint8_t VOICE_1K[] = {0x00U,
|
||||
0xCEU, 0xA8U, 0xFEU, 0x83U, 0xACU, 0xC4U, 0x58U, 0x20U, 0x0AU, 0xCEU, 0xA8U,
|
||||
0xFEU, 0x83U, 0xA0U, 0x00U, 0x00U, 0x00U, 0x00U, 0x00U, 0x0CU, 0xC4U, 0x58U,
|
||||
0x20U, 0x0AU, 0xCEU, 0xA8U, 0xFEU, 0x83U, 0xACU, 0xC4U, 0x58U, 0x20U, 0x0AU};
|
||||
|
||||
// Embedded LC: CC: 1, srcID: 1, dstID: TG9
|
||||
const uint8_t SYNCEMB_1K[6][7] = {
|
||||
{0x07U, 0x55U, 0xFDU, 0x7DU, 0xF7U, 0x5FU, 0x70U}, // BS VOICE SYNC (audio seq 0)
|
||||
{0x01U, 0x30U, 0x00U, 0x00U, 0x90U, 0x09U, 0x10U}, // EMB + Embedded LC1 (audio seq 1)
|
||||
{0x01U, 0x70U, 0x00U, 0x90U, 0x00U, 0x07U, 0x40U}, // EMB + Embedded LC2 (audio seq 2)
|
||||
{0x01U, 0x70U, 0x00U, 0x31U, 0x40U, 0x07U, 0x40U}, // EMB + Embedded LC3 (audio seq 3)
|
||||
{0x01U, 0x50U, 0xA1U, 0x71U, 0xD1U, 0x70U, 0x70U}, // EMB + Embedded LC4 (audio seq 4)
|
||||
{0x01U, 0x10U, 0x00U, 0x00U, 0x00U, 0x0EU, 0x20U}}; // EMB (audio seq 5)
|
||||
|
||||
// Short LC:
|
||||
// TS1: dstID: 0, ACTIVITY_NONE
|
||||
// TS2: dstID: TG9, ACTIVITY_VOICE
|
||||
const uint8_t SHORTLC_1K[] = {0x33U, 0x3AU, 0xA0U, 0x30U, 0x00U, 0x55U, 0xA6U, 0x5FU, 0x50U};
|
||||
|
||||
CCalDMR::CCalDMR() :
|
||||
m_transmit(false)
|
||||
m_transmit(false),
|
||||
m_state(DMR1KCAL_IDLE),
|
||||
m_frame_start(0U),
|
||||
m_dmr1k(),
|
||||
m_audioSeq(0)
|
||||
{
|
||||
::memcpy(m_dmr1k, VOICE_1K, DMR_FRAME_LENGTH_BYTES + 1U);
|
||||
}
|
||||
|
||||
void CCalDMR::process()
|
||||
{
|
||||
if (m_transmit) {
|
||||
dmrTX.setCal(true);
|
||||
dmrTX.process();
|
||||
} else {
|
||||
dmrTX.setCal(false);
|
||||
switch (m_modemState) {
|
||||
case STATE_DMRCAL:
|
||||
case STATE_LFCAL:
|
||||
if (m_transmit) {
|
||||
dmrTX.setCal(true);
|
||||
dmrTX.process();
|
||||
} else {
|
||||
dmrTX.setCal(false);
|
||||
}
|
||||
break;
|
||||
case STATE_DMR1KCAL:
|
||||
dmr1kcal();
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void CCalDMR::createData1k(uint8_t n)
|
||||
{
|
||||
for(uint8_t i = 0; i < 5U; i++)
|
||||
m_dmr1k[i + 15U] = SYNCEMB_1K[n][i + 1U];
|
||||
|
||||
m_dmr1k[14U] &= 0xF0U;
|
||||
m_dmr1k[20U] &= 0x0FU;
|
||||
m_dmr1k[14U] |= SYNCEMB_1K[n][0] & 0x0FU;
|
||||
m_dmr1k[20U] |= SYNCEMB_1K[n][6] & 0xF0U;
|
||||
}
|
||||
|
||||
void CCalDMR::dmr1kcal()
|
||||
{
|
||||
dmrTX.process();
|
||||
|
||||
uint16_t space = dmrTX.getSpace2();
|
||||
if (space < 1U)
|
||||
return;
|
||||
|
||||
switch (m_state) {
|
||||
case DMR1KCAL_VH:
|
||||
dmrTX.setColorCode(1U);
|
||||
dmrTX.writeShortLC(SHORTLC_1K, 9U);
|
||||
dmrTX.writeData2(VH_1K, DMR_FRAME_LENGTH_BYTES + 1U);
|
||||
dmrTX.setStart(true);
|
||||
m_state = DMR1KCAL_VOICE;
|
||||
break;
|
||||
case DMR1KCAL_VOICE:
|
||||
createData1k(m_audioSeq);
|
||||
dmrTX.writeData2(m_dmr1k, DMR_FRAME_LENGTH_BYTES + 1U);
|
||||
if(m_audioSeq == 5U) {
|
||||
m_audioSeq = 0U;
|
||||
if(!m_transmit)
|
||||
m_state = DMR1KCAL_VT;
|
||||
} else
|
||||
m_audioSeq++;
|
||||
break;
|
||||
case DMR1KCAL_VT:
|
||||
dmrTX.writeData2(VT_1K, DMR_FRAME_LENGTH_BYTES + 1U);
|
||||
m_frame_start = dmrTX.getFrameCount();
|
||||
m_state = DMR1KCAL_WAIT;
|
||||
break;
|
||||
case DMR1KCAL_WAIT:
|
||||
if (dmrTX.getFrameCount() > (m_frame_start + 30U)) {
|
||||
dmrTX.setStart(false);
|
||||
dmrTX.resetFifo2();
|
||||
m_audioSeq = 0U;
|
||||
m_state = DMR1KCAL_IDLE;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
m_state = DMR1KCAL_IDLE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -44,6 +146,9 @@ uint8_t CCalDMR::write(const uint8_t* data, uint8_t length)
|
|||
|
||||
m_transmit = data[0U] == 1U;
|
||||
|
||||
if(m_transmit && m_state == DMR1KCAL_IDLE && m_modemState == STATE_DMR1KCAL)
|
||||
m_state = DMR1KCAL_VH;
|
||||
|
||||
return 0U;
|
||||
}
|
||||
|
||||
|
|
16
CalDMR.h
16
CalDMR.h
|
@ -23,16 +23,30 @@
|
|||
#include "Config.h"
|
||||
#include "DMRDefines.h"
|
||||
|
||||
enum DMR1KCAL {
|
||||
DMR1KCAL_IDLE,
|
||||
DMR1KCAL_VH,
|
||||
DMR1KCAL_VOICE,
|
||||
DMR1KCAL_VT,
|
||||
DMR1KCAL_WAIT
|
||||
};
|
||||
|
||||
class CCalDMR {
|
||||
public:
|
||||
CCalDMR();
|
||||
|
||||
void process();
|
||||
void dmr1kcal();
|
||||
void createData1k(uint8_t n);
|
||||
|
||||
uint8_t write(const uint8_t* data, uint8_t length);
|
||||
|
||||
private:
|
||||
bool m_transmit;
|
||||
bool m_transmit;
|
||||
DMR1KCAL m_state;
|
||||
uint32_t m_frame_start;
|
||||
uint8_t m_dmr1k[DMR_FRAME_LENGTH_BYTES + 1U];
|
||||
uint8_t m_audioSeq;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
14
DMRTX.cpp
14
DMRTX.cpp
|
@ -389,3 +389,17 @@ void CDMRTX::setColorCode(uint8_t colorCode)
|
|||
slotType.encode(colorCode, DT_IDLE, m_idle);
|
||||
}
|
||||
|
||||
void CDMRTX::resetFifo1()
|
||||
{
|
||||
m_fifo[0U].reset();
|
||||
}
|
||||
|
||||
void CDMRTX::resetFifo2()
|
||||
{
|
||||
m_fifo[1U].reset();
|
||||
}
|
||||
|
||||
uint32_t CDMRTX::getFrameCount()
|
||||
{
|
||||
return m_frameCount;
|
||||
}
|
||||
|
|
6
DMRTX.h
6
DMRTX.h
|
@ -48,7 +48,11 @@ public:
|
|||
void setCal(bool start);
|
||||
|
||||
void process();
|
||||
|
||||
|
||||
void resetFifo1();
|
||||
void resetFifo2();
|
||||
uint32_t getFrameCount();
|
||||
|
||||
uint8_t getSpace1() const;
|
||||
uint8_t getSpace2() const;
|
||||
|
||||
|
|
|
@ -50,6 +50,7 @@ enum MMDVM_STATE {
|
|||
STATE_P25 = 4,
|
||||
|
||||
// Dummy states start at 90
|
||||
STATE_DMR1KCAL = 94,
|
||||
STATE_LFCAL = 95,
|
||||
STATE_RSSICAL = 96,
|
||||
STATE_CWID = 97,
|
||||
|
|
|
@ -93,7 +93,7 @@ void loop()
|
|||
if (m_modemState == STATE_DSTARCAL)
|
||||
calDStarTX.process();
|
||||
|
||||
if (m_modemState == STATE_DMRCAL || m_modemState == STATE_LFCAL)
|
||||
if (m_modemState == STATE_DMRCAL || m_modemState == STATE_LFCAL || m_modemState == STATE_DMR1KCAL)
|
||||
calDMR.process();
|
||||
|
||||
if (m_modemState == STATE_IDLE)
|
||||
|
|
|
@ -90,7 +90,7 @@ void loop()
|
|||
if (m_modemState == STATE_DSTARCAL)
|
||||
calDStarTX.process();
|
||||
|
||||
if (m_modemState == STATE_DMRCAL || m_modemState == STATE_LFCAL)
|
||||
if (m_modemState == STATE_DMRCAL || m_modemState == STATE_LFCAL || m_modemState == STATE_DMR1KCAL)
|
||||
calDMR.process();
|
||||
|
||||
if (m_modemState == STATE_IDLE)
|
||||
|
|
|
@ -243,7 +243,7 @@ uint8_t CSerialPort::setConfig(const uint8_t* data, uint8_t length)
|
|||
|
||||
MMDVM_STATE modemState = MMDVM_STATE(data[3U]);
|
||||
|
||||
if (modemState != STATE_IDLE && modemState != STATE_DSTAR && modemState != STATE_DMR && modemState != STATE_YSF && modemState != STATE_P25 && modemState != STATE_DSTARCAL && modemState != STATE_DMRCAL && modemState != STATE_RSSICAL && modemState != STATE_LFCAL)
|
||||
if (modemState != STATE_IDLE && modemState != STATE_DSTAR && modemState != STATE_DMR && modemState != STATE_YSF && modemState != STATE_P25 && modemState != STATE_DSTARCAL && modemState != STATE_DMRCAL && modemState != STATE_RSSICAL && modemState != STATE_LFCAL && modemState != STATE_DMR1KCAL)
|
||||
return 4U;
|
||||
if (modemState == STATE_DSTAR && !dstarEnable)
|
||||
return 4U;
|
||||
|
@ -309,7 +309,7 @@ uint8_t CSerialPort::setMode(const uint8_t* data, uint8_t length)
|
|||
if (modemState == m_modemState)
|
||||
return 0U;
|
||||
|
||||
if (modemState != STATE_IDLE && modemState != STATE_DSTAR && modemState != STATE_DMR && modemState != STATE_YSF && modemState != STATE_P25 && modemState != STATE_DSTARCAL && modemState != STATE_DMRCAL && modemState != STATE_RSSICAL && modemState != STATE_LFCAL)
|
||||
if (modemState != STATE_IDLE && modemState != STATE_DSTAR && modemState != STATE_DMR && modemState != STATE_YSF && modemState != STATE_P25 && modemState != STATE_DSTARCAL && modemState != STATE_DMRCAL && modemState != STATE_RSSICAL && modemState != STATE_LFCAL && modemState != STATE_DMR1KCAL)
|
||||
return 4U;
|
||||
if (modemState == STATE_DSTAR && !m_dstarEnable)
|
||||
return 4U;
|
||||
|
@ -402,6 +402,16 @@ void CSerialPort::setMode(MMDVM_STATE modemState)
|
|||
p25RX.reset();
|
||||
cwIdTX.reset();
|
||||
break;
|
||||
case STATE_DMR1KCAL:
|
||||
DEBUG1("Mode set to DMR 1031 Hz Calibrate");
|
||||
dmrIdleRX.reset();
|
||||
dmrDMORX.reset();
|
||||
dmrRX.reset();
|
||||
dstarRX.reset();
|
||||
ysfRX.reset();
|
||||
p25RX.reset();
|
||||
cwIdTX.reset();
|
||||
break;
|
||||
default:
|
||||
DEBUG1("Mode set to Idle");
|
||||
// STATE_IDLE
|
||||
|
@ -483,7 +493,7 @@ void CSerialPort::process()
|
|||
case MMDVM_CAL_DATA:
|
||||
if (m_modemState == STATE_DSTARCAL)
|
||||
err = calDStarTX.write(m_buffer + 3U, m_len - 3U);
|
||||
if (m_modemState == STATE_DMRCAL || m_modemState == STATE_LFCAL)
|
||||
if (m_modemState == STATE_DMRCAL || m_modemState == STATE_LFCAL || m_modemState == STATE_DMR1KCAL)
|
||||
err = calDMR.write(m_buffer + 3U, m_len - 3U);
|
||||
if (err == 0U) {
|
||||
sendACK();
|
||||
|
|
Loading…
Reference in New Issue