6#include "AudioTools/Communication/FEC/ReedSolomon/rs.hpp"
12inline uint16_t
crc16(
const uint8_t* data,
size_t len, uint16_t crc = 0xFFFF) {
13 for (
size_t i = 0; i < len; i++) {
14 crc ^= (uint16_t)data[i] << 8;
15 for (
int b = 0; b < 8; b++)
16 crc = (crc & 0x8000) ? (crc << 1) ^ 0x1021 : (crc << 1);
35 static constexpr uint8_t
FLAG = 0x7E;
36 static constexpr uint8_t
ESC = 0x7D;
55template <u
int8_t MAX_PAYLOAD = 64, u
int8_t ECC_BYTES = 16>
57 static_assert(MAX_PAYLOAD >= 1,
"MAX_PAYLOAD must be at least 1");
58 static_assert(ECC_BYTES >= 2,
"ECC_BYTES must be at least 2");
60 "a packet is limited to 255 bytes");
68 size_t write(uint8_t ch)
override {
return write(&ch, 1); }
70 size_t write(
const uint8_t* data,
size_t len)
override {
71 if (
p_out ==
nullptr)
return 0;
72 for (
size_t j = 0; j < len; j++) {
92 RS::ReedSolomon<MSG_LEN, ECC_BYTES>
rs;
97 uint8_t codeword[
MSG_LEN + ECC_BYTES];
103 rs.Encode(msg, codeword);
128template <u
int8_t MAX_PAYLOAD = 64, u
int8_t ECC_BYTES = 16>
159 size_t write(
const uint8_t* data,
size_t len)
override {
160 for (
size_t j = 0; j < len; j++)
write(data[j]);
184 RS::ReedSolomon<MSG_LEN, ECC_BYTES>
rs;
195 memcpy(codeword + skip,
frame, n);
197 if (
rs.Decode(codeword, msg) != 0) {
202 for (
int j = 0; j < skip; j++) {
209 const uint8_t* payload = msg + skip;
210 uint16_t crc =
crc16(payload, payload_len);
211 if (msg[
MSG_LEN - 2] != (crc >> 8) || msg[
MSG_LEN - 1] != (crc & 0xFF)) {
217 rs.Encode(msg, corrected);
220 if (corrected[j] != codeword[j]) errors++;
224 stats.corrected_bytes += errors;
226 if (
p_out !=
nullptr)
p_out->write(payload, payload_len);
245template <u
int8_t MAX_PAYLOAD = 64, u
int8_t ECC_BYTES = 16>
282 size_t write(
const uint8_t* data,
size_t len)
override {
283 return encoder.write(data, len);
324 if (
p_in ==
nullptr)
return;
327 while ((len =
p_in->available()) > 0) {
328 if (len > (
int)
sizeof(buffer)) len =
sizeof(buffer);
329 len =
p_in->readBytes(buffer, len);
FIFO for received data which grows when needed: e.g. one decoding step can produce more data than exp...
Definition ModemBase.h:249
Receives the packets of a PacketEncoder: the written bytes (e.g. the output of a modem decoder) are d...
Definition PacketStream.h:129
static constexpr int MAX_FRAME
Definition PacketStream.h:177
bool overflow
Definition PacketStream.h:181
uint8_t frame[MAX_FRAME]
Definition PacketStream.h:179
int frame_len
Definition PacketStream.h:180
const PacketStatistics & statistics() const
Statistics of the received packets.
Definition PacketStream.h:165
void reset()
Resets the statistics and drops an incomplete frame.
Definition PacketStream.h:168
void setOutput(Print &out)
Definition PacketStream.h:134
Print * p_out
Definition PacketStream.h:178
void processFrame()
Definition PacketStream.h:186
PacketDecoder(Print &out)
Definition PacketStream.h:132
PacketStatistics stats
Definition PacketStream.h:183
RS::ReedSolomon< MSG_LEN, ECC_BYTES > rs
Definition PacketStream.h:184
size_t write(uint8_t ch) override
Definition PacketStream.h:136
bool escaped
Definition PacketStream.h:182
static constexpr int MSG_LEN
Definition PacketStream.h:176
size_t write(const uint8_t *data, size_t len) override
Definition PacketStream.h:159
Splits the written data into packets with a CRC-16 and Reed-Solomon forward error correction,...
Definition PacketStream.h:56
uint8_t payload[MAX_PAYLOAD]
Definition PacketStream.h:90
int pending() const
Number of buffered bytes which were not sent yet.
Definition PacketStream.h:85
int payload_len
Definition PacketStream.h:91
Print * p_out
Definition PacketStream.h:89
void writePacket()
Definition PacketStream.h:94
size_t write(const uint8_t *data, size_t len) override
Definition PacketStream.h:70
void setOutput(Print &out)
Definition PacketStream.h:66
void writeEscaped(uint8_t b)
Definition PacketStream.h:111
PacketEncoder(Print &out)
Definition PacketStream.h:64
size_t write(uint8_t ch) override
Definition PacketStream.h:68
static constexpr int MSG_LEN
Definition PacketStream.h:88
RS::ReedSolomon< MSG_LEN, ECC_BYTES > rs
Definition PacketStream.h:92
void flush() override
Sends the buffered data as packet.
Definition PacketStream.h:80
bool begin()
Resets the receive state and the statistics.
Definition PacketStream.h:273
PacketStream()
Definition PacketStream.h:248
void flush() override
Sends the buffered data as packet and flushes the underlying stream.
Definition PacketStream.h:287
Print * p_out
Definition PacketStream.h:339
size_t readBytes(char *data, size_t len)
Definition PacketStream.h:318
int available() override
Definition PacketStream.h:292
int read() override
Definition PacketStream.h:297
PacketEncoder< MAX_PAYLOAD, ECC_BYTES > encoder
Definition PacketStream.h:341
size_t readBytes(uint8_t *data, size_t len)
Reads the available data (does not wait for more data).
Definition PacketStream.h:308
Stream * p_in
Definition PacketStream.h:340
const PacketStatistics & statistics() const
Statistics of the received packets.
Definition PacketStream.h:336
PacketDecoder< MAX_PAYLOAD, ECC_BYTES > decoder
Definition PacketStream.h:342
void update()
Reads the available data from the underlying stream.
Definition PacketStream.h:323
void setOutput(Print &out)
Defines the output (send only).
Definition PacketStream.h:267
ByteQueue rx_queue
Definition PacketStream.h:343
PacketStream(Print &out)
send only
Definition PacketStream.h:255
void setStream(Stream &io)
Defines the stream for sending and receiving.
Definition PacketStream.h:261
int peek() override
Definition PacketStream.h:302
size_t write(uint8_t ch) override
Definition PacketStream.h:280
size_t write(const uint8_t *data, size_t len) override
Definition PacketStream.h:282
PacketStream(Stream &io)
send and receive
Definition PacketStream.h:250
TinyModem: software audio modems and packets with error correction.
Definition AX25.h:11
uint16_t crc16(const uint8_t *data, size_t len, uint16_t crc=0xFFFF)
CRC-16-CCITT (polynomial 0x1021, initial value 0xFFFF).
Definition PacketStream.h:12
Statistics of the received packets.
Definition PacketStream.h:22
unsigned dropped
frames which could not be corrected or failed the CRC check
Definition PacketStream.h:30
unsigned corrected_bytes
number of corrected bytes
Definition PacketStream.h:28
unsigned corrected
delivered packets which needed an error correction
Definition PacketStream.h:26
unsigned received
packets which were delivered
Definition PacketStream.h:24