[EXPERIMENTAL] initial TIA-102 DFSI packet support (not enabled yet);

82-dvmbridge---implement-notch-filter-for-2175hz-trc-guard-tone
Bryan Biedenkapp 1 year ago
parent ddda823b55
commit 2d450f64b0

@ -4,7 +4,7 @@
* GPLv2 Open Source. Use is subject to license terms. * GPLv2 Open Source. Use is subject to license terms.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* Copyright (C) 2024 Bryan Biedenkapp, N2PLL * Copyright (C) 2024-2025 Bryan Biedenkapp, N2PLL
* *
*/ */
#include "common/p25/dfsi/frames/BlockHeader.h" #include "common/p25/dfsi/frames/BlockHeader.h"
@ -26,8 +26,10 @@ using namespace p25::dfsi::frames;
/* Initializes a instance of the BlockHeader class. */ /* Initializes a instance of the BlockHeader class. */
BlockHeader::BlockHeader() : BlockHeader::BlockHeader() :
m_payloadType(false), m_payloadType(true),
m_blockLength(BlockType::UNDEFINED) m_blockType(BlockType::UNDEFINED),
m_timestampOffset(0U),
m_blockLength(0U)
{ {
/* stub */ /* stub */
} }
@ -35,8 +37,10 @@ BlockHeader::BlockHeader() :
/* Initializes a instance of the BlockHeader class. */ /* Initializes a instance of the BlockHeader class. */
BlockHeader::BlockHeader(uint8_t* data, bool verbose) : BlockHeader::BlockHeader(uint8_t* data, bool verbose) :
m_payloadType(false), m_payloadType(true),
m_blockLength(BlockType::UNDEFINED) m_blockType(BlockType::UNDEFINED),
m_timestampOffset(0U),
m_blockLength(0U)
{ {
decode(data, verbose); decode(data, verbose);
} }

@ -4,7 +4,7 @@
* GPLv2 Open Source. Use is subject to license terms. * GPLv2 Open Source. Use is subject to license terms.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* Copyright (C) 2024 Bryan Biedenkapp, N2PLL * Copyright (C) 2024-2025 Bryan Biedenkapp, N2PLL
* *
*/ */
/** /**
@ -53,8 +53,8 @@ namespace p25
*/ */
class HOST_SW_API BlockHeader { class HOST_SW_API BlockHeader {
public: public:
static const uint8_t LENGTH = 1; static const uint8_t LENGTH = 1U;
static const uint8_t VERBOSE_LENGTH = 4; static const uint8_t VERBOSE_LENGTH = 4U;
/** /**
* @brief Initializes a copy instance of the BlockHeader class. * @brief Initializes a copy instance of the BlockHeader class.

@ -4,7 +4,7 @@
* GPLv2 Open Source. Use is subject to license terms. * GPLv2 Open Source. Use is subject to license terms.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* Copyright (C) 2024 Bryan Biedenkapp, N2PLL * Copyright (C) 2024-2025 Bryan Biedenkapp, N2PLL
* *
*/ */
/** /**
@ -45,7 +45,7 @@ namespace p25
*/ */
class HOST_SW_API ControlOctet { class HOST_SW_API ControlOctet {
public: public:
static const uint8_t LENGTH = 1; static const uint8_t LENGTH = 1U;
/** /**
* @brief Initializes a copy instance of the ControlOctet class. * @brief Initializes a copy instance of the ControlOctet class.

@ -4,7 +4,7 @@
* GPLv2 Open Source. Use is subject to license terms. * GPLv2 Open Source. Use is subject to license terms.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* Copyright (C) 2024 Bryan Biedenkapp, N2PLL * Copyright (C) 2024-2025 Bryan Biedenkapp, N2PLL
* *
*/ */
#include "common/p25/dfsi/frames/FullRateVoice.h" #include "common/p25/dfsi/frames/FullRateVoice.h"
@ -95,7 +95,15 @@ bool FullRateVoice::decode(const uint8_t* data)
// CAI 9 and 10 are 3 bytes of additional data not 4 // CAI 9 and 10 are 3 bytes of additional data not 4
::memcpy(additionalData, data + 14U, ADDITIONAL_LENGTH - 1U); ::memcpy(additionalData, data + 14U, ADDITIONAL_LENGTH - 1U);
} else { } else {
::memcpy(additionalData, data + 14U, ADDITIONAL_LENGTH); uint8_t buffer[ADDITIONAL_LENGTH - 1U];
::memset(buffer, 0x00U, ADDITIONAL_LENGTH - 1U);
::memcpy(buffer, data + 14U, ADDITIONAL_LENGTH - 1U);
buffer[2U] &= 0xC0U; // mask low bits
uint32_t offset = 0;
for (uint8_t i = 0; i < ADDITIONAL_LENGTH - 1U; i++, offset += 6) {
Utils::hex2Bin(additionalData[i], buffer, offset);
}
} }
} else { } else {
if (additionalData != nullptr) if (additionalData != nullptr)
@ -128,7 +136,16 @@ void FullRateVoice::encode(uint8_t* data)
// CAI 9 and 10 are 3 bytes of additional data not 4 // CAI 9 and 10 are 3 bytes of additional data not 4
::memcpy(data + 14U, additionalData, ADDITIONAL_LENGTH - 1U); ::memcpy(data + 14U, additionalData, ADDITIONAL_LENGTH - 1U);
} else { } else {
::memcpy(data + 14U, additionalData, ADDITIONAL_LENGTH); uint8_t buffer[ADDITIONAL_LENGTH - 1U];
::memset(buffer, 0x00U, ADDITIONAL_LENGTH - 1U);
::memcpy(buffer, additionalData, ADDITIONAL_LENGTH - 1U);
uint32_t offset = 0;
for (uint8_t i = 0; i < ADDITIONAL_LENGTH - 1U; i++, offset += 6) {
buffer[i] = Utils::bin2Hex(additionalData, offset);
}
::memcpy(data + 14U, buffer, ADDITIONAL_LENGTH);
} }
} }
} }

@ -4,7 +4,7 @@
* GPLv2 Open Source. Use is subject to license terms. * GPLv2 Open Source. Use is subject to license terms.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* Copyright (C) 2024 Bryan Biedenkapp, N2PLL * Copyright (C) 2024-2025 Bryan Biedenkapp, N2PLL
* *
*/ */
/** /**
@ -133,10 +133,10 @@ namespace p25
* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
* | IMBE 8 | IMBE 9 | IMBE 10 | IMBE 11 | * | IMBE 8 | IMBE 9 | IMBE 10 | IMBE 11 |
* +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ * +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
* | Et | Er |M|L|E| E1 |SF | B | Link Ctrl | Link Ctrl | * | Et | Er |M|L|E| E1 |SF | B | Link Ctrl | Link Ctrl | Link |
* | | | | |4| | | | | | * | | | | |4| | | | | | |
* +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ * +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
* | Link Ctrl |R| Status | * |Ctr|R| Status | Rsvd |
* +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ * +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
* *
* CAI Frames 12 - 17. * CAI Frames 12 - 17.
@ -150,10 +150,10 @@ namespace p25
* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
* | IMBE 8 | IMBE 9 | IMBE 10 | IMBE 11 | * | IMBE 8 | IMBE 9 | IMBE 10 | IMBE 11 |
* +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ * +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
* | Et | Er |M|L|E| E1 |SF | B | Enc Sync | Enc Sync | * | Et | Er |M|L|E| E1 |SF | B | Enc Sync | Enc Sync | Enc |
* | | | | |4| | | | | | * | | | | |4| | | | | | |
* +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ * +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
* | Enc Sync |R| Status | * |Syn|R| Status | Rsvd |
* +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ * +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
* *
* CAI Frames 9 and 10. * CAI Frames 9 and 10.
@ -177,9 +177,9 @@ namespace p25
*/ */
class HOST_SW_API FullRateVoice { class HOST_SW_API FullRateVoice {
public: public:
static const uint8_t LENGTH = 18; static const uint8_t LENGTH = 18U;
static const uint8_t ADDITIONAL_LENGTH = 4; static const uint8_t ADDITIONAL_LENGTH = 4U;
static const uint8_t IMBE_BUF_LEN = 11; static const uint8_t IMBE_BUF_LEN = 11U;
/** /**
* @brief Initializes a copy instance of the FullRateVoice class. * @brief Initializes a copy instance of the FullRateVoice class.

@ -55,9 +55,9 @@ namespace p25
*/ */
class HOST_SW_API MotFullRateVoice { class HOST_SW_API MotFullRateVoice {
public: public:
static const uint8_t LENGTH = 17; static const uint8_t LENGTH = 17U;
static const uint8_t SHORTENED_LENGTH = 14; static const uint8_t SHORTENED_LENGTH = 14U;
static const uint8_t ADDITIONAL_LENGTH = 4; static const uint8_t ADDITIONAL_LENGTH = 4U;
/** /**
* @brief Initializes a copy instance of the MotFullRateVoice class. * @brief Initializes a copy instance of the MotFullRateVoice class.

@ -55,7 +55,7 @@ namespace p25
*/ */
class HOST_SW_API MotPDUFrame { class HOST_SW_API MotPDUFrame {
public: public:
static const uint8_t LENGTH = 20; static const uint8_t LENGTH = 20U;
/** /**
* @brief Initializes a copy instance of the MotPDUFrame class. * @brief Initializes a copy instance of the MotPDUFrame class.

@ -50,8 +50,8 @@ namespace p25
*/ */
class HOST_SW_API MotStartOfStream { class HOST_SW_API MotStartOfStream {
public: public:
static const uint8_t LENGTH = 10; static const uint8_t LENGTH = 10U;
static const uint8_t FIXED_MARKER = 0x02; static const uint8_t FIXED_MARKER = 0x02U;
/** /**
* @brief Initializes a copy instance of the MotStartOfStream class. * @brief Initializes a copy instance of the MotStartOfStream class.

@ -58,7 +58,7 @@ namespace p25
*/ */
class HOST_SW_API MotStartVoiceFrame { class HOST_SW_API MotStartVoiceFrame {
public: public:
static const uint8_t LENGTH = 22; static const uint8_t LENGTH = 22U;
/** /**
* @brief Initializes a copy instance of the MotStartVoiceFrame class. * @brief Initializes a copy instance of the MotStartVoiceFrame class.

@ -57,7 +57,7 @@ namespace p25
*/ */
class HOST_SW_API MotTSBKFrame { class HOST_SW_API MotTSBKFrame {
public: public:
static const uint8_t LENGTH = 24; static const uint8_t LENGTH = 24U;
/** /**
* @brief Initializes a copy instance of the MotTSBKFrame class. * @brief Initializes a copy instance of the MotTSBKFrame class.

@ -61,8 +61,8 @@ namespace p25
*/ */
class HOST_SW_API MotVoiceHeader1 { class HOST_SW_API MotVoiceHeader1 {
public: public:
static const uint8_t LENGTH = 30; static const uint8_t LENGTH = 30U;
static const uint8_t HCW_LENGTH = 21; static const uint8_t HCW_LENGTH = 21U;
/** /**
* @brief Initializes a copy instance of the MotVoiceHeader1 class. * @brief Initializes a copy instance of the MotVoiceHeader1 class.

@ -57,8 +57,8 @@ namespace p25
*/ */
class HOST_SW_API MotVoiceHeader2 { class HOST_SW_API MotVoiceHeader2 {
public: public:
static const uint8_t LENGTH = 22; static const uint8_t LENGTH = 22U;
static const uint8_t HCW_LENGTH = 20; static const uint8_t HCW_LENGTH = 20U;
/** /**
* @brief Initializes a copy instance of the MotVoiceHeader2 class. * @brief Initializes a copy instance of the MotVoiceHeader2 class.

@ -4,7 +4,7 @@
* GPLv2 Open Source. Use is subject to license terms. * GPLv2 Open Source. Use is subject to license terms.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* Copyright (C) 2024 Bryan Biedenkapp, N2PLL * Copyright (C) 2024-2025 Bryan Biedenkapp, N2PLL
* *
*/ */
/** /**
@ -45,7 +45,7 @@ namespace p25
*/ */
class HOST_SW_API StartOfStream { class HOST_SW_API StartOfStream {
public: public:
static const uint8_t LENGTH = 4; static const uint8_t LENGTH = 4U;
/** /**
* @brief Initializes a copy instance of the StartOfStream class. * @brief Initializes a copy instance of the StartOfStream class.

@ -96,14 +96,17 @@ LC& LC::operator=(const LC& data)
/* Decode a header data unit. */ /* Decode a header data unit. */
bool LC::decodeHDU(const uint8_t* data) bool LC::decodeHDU(const uint8_t* data, bool rawOnly)
{ {
assert(data != nullptr); assert(data != nullptr);
// deinterleave // deinterleave
uint8_t rs[P25_HDU_LENGTH_BYTES + 1U]; uint8_t rs[P25_HDU_LENGTH_BYTES + 1U];
uint8_t raw[P25_HDU_LENGTH_BYTES + 1U]; uint8_t raw[P25_HDU_LENGTH_BYTES + 1U];
P25Utils::decode(data, raw, 114U, 780U); if (rawOnly)
::memcpy(raw, data, P25_HDU_LENGTH_BYTES);
else
P25Utils::decode(data, raw, 114U, 780U);
// decode Golay (18,6,8) FEC // decode Golay (18,6,8) FEC
decodeHDUGolay(raw, rs); decodeHDUGolay(raw, rs);
@ -167,7 +170,7 @@ bool LC::decodeHDU(const uint8_t* data)
/* Encode a header data unit. */ /* Encode a header data unit. */
void LC::encodeHDU(uint8_t* data) void LC::encodeHDU(uint8_t* data, bool rawOnly)
{ {
assert(data != nullptr); assert(data != nullptr);
assert(m_mi != nullptr); assert(m_mi != nullptr);
@ -202,6 +205,11 @@ void LC::encodeHDU(uint8_t* data)
// encode Golay (18,6,8) FEC // encode Golay (18,6,8) FEC
encodeHDUGolay(raw, rs); encodeHDUGolay(raw, rs);
if (rawOnly) {
::memcpy(data, raw, P25_HDU_LENGTH_BYTES);
return;
}
// interleave // interleave
P25Utils::encode(raw, data, 114U, 780U); P25Utils::encode(raw, data, 114U, 780U);

@ -73,14 +73,16 @@ namespace p25
/** /**
* @brief Decode a header data unit. * @brief Decode a header data unit.
* @param[in] data Buffer containing the HDU to decode. * @param[in] data Buffer containing the HDU to decode.
* @param rawOnly Flag indicating only the raw bytes of the LC should be decoded.
* @returns True, if HDU decoded, otherwise false. * @returns True, if HDU decoded, otherwise false.
*/ */
bool decodeHDU(const uint8_t* data); bool decodeHDU(const uint8_t* data, bool rawOnly = false);
/** /**
* @brief Encode a header data unit. * @brief Encode a header data unit.
* @param[out] data Buffer to encode an HDU. * @param[out] data Buffer to encode an HDU.
* @param rawOnly Flag indicating only the raw bytes of the LC should be encoded.
*/ */
void encodeHDU(uint8_t* data); void encodeHDU(uint8_t* data, bool rawOnly = false);
/** /**
* @brief Decode a logical link data unit 1. * @brief Decode a logical link data unit 1.

File diff suppressed because it is too large Load Diff

@ -4,7 +4,7 @@
* GPLv2 Open Source. Use is subject to license terms. * GPLv2 Open Source. Use is subject to license terms.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* Copyright (C) 2024 Bryan Biedenkapp, N2PLL * Copyright (C) 2024-2025 Bryan Biedenkapp, N2PLL
* *
*/ */
/** /**
@ -261,6 +261,12 @@ namespace modem
*/ */
void setP25NAC(uint32_t nac) override; void setP25NAC(uint32_t nac) override;
/**
* @brief Helper to set the TIA-102 format DFSI frame flag.
* @param set
*/
void setTIAFormat(bool set);
/** /**
* @brief Opens connection to the air interface modem. * @brief Opens connection to the air interface modem.
* @returns bool True, if connection to modem is made, otherwise false. * @returns bool True, if connection to modem is made, otherwise false.
@ -316,6 +322,8 @@ namespace modem
edac::RS634717 m_rs; edac::RS634717 m_rs;
bool m_useTIAFormat;
/** /**
* @brief Helper to write data from the P25 Tx queue to the serial interface. * @brief Helper to write data from the P25 Tx queue to the serial interface.
* @return int Actual number of bytes written to the serial interface. * @return int Actual number of bytes written to the serial interface.
@ -340,6 +348,12 @@ namespace modem
* @param length Length of buffer. * @param length Length of buffer.
*/ */
void convertToAir(const uint8_t *data, uint32_t length); void convertToAir(const uint8_t *data, uint32_t length);
/**
* @brief Internal helper to convert from TIA-102 DFSI to TIA-102 air interface.
* @param data Buffer containing data to convert.
* @param length Length of buffer.
*/
void convertToAirTIA(const uint8_t *data, uint32_t length);
/** /**
* @brief Helper to add a V.24 data frame to the P25 Tx queue with the proper timestamp and formatting. * @brief Helper to add a V.24 data frame to the P25 Tx queue with the proper timestamp and formatting.
@ -359,12 +373,35 @@ namespace modem
*/ */
void endOfStream(); void endOfStream();
/**
* @brief Helper to generate the NID value.
* @param duid P25 DUID.
* @returns uint16_t P25 NID.
*/
uint16_t generateNID(P25DEF::DUID::E duid = P25DEF::DUID::LDU1);
/**
* @brief Send a start of stream sequence (HDU, etc) to the connected UDP TIA-102 device.
* @param[in] control Instance of p25::lc::LC containing link control data.
*/
void startOfStreamTIA(const p25::lc::LC& control);
/**
* @brief Send an end of stream sequence (TDU, etc) to the connected UDP TIA-102 device.
*/
void endOfStreamTIA();
/** /**
* @brief Internal helper to convert from TIA-102 air interface to V.24/DFSI. * @brief Internal helper to convert from TIA-102 air interface to V.24/DFSI.
* @param data Buffer containing data to convert. * @param data Buffer containing data to convert.
* @param length Length of buffer. * @param length Length of buffer.
*/ */
void convertFromAir(uint8_t* data, uint32_t length); void convertFromAir(uint8_t* data, uint32_t length);
/**
* @brief Internal helper to convert from TIA-102 air interface to TIA-102 DFSI.
* @param data Buffer containing data to convert.
* @param length Length of buffer.
*/
void convertFromAirTIA(uint8_t* data, uint32_t length);
}; };
} // namespace modem } // namespace modem

Loading…
Cancel
Save

Powered by TurnKey Linux.