15uint16_t pc_interbus_fcs(
const uint8_t *bytes,
size_t len)
23size_t pc_interbus_build(
const uint16_t *words,
size_t word_count, uint8_t *out,
size_t cap)
25 if (!out || (word_count && !words))
29 size_t n = 2 + word_count * 2 + 2;
35 out[i++] = (uint8_t)(PC_INTERBUS_LOOPBACK >> 8);
36 out[i++] = (uint8_t)PC_INTERBUS_LOOPBACK;
37 for (
size_t w = 0; w < word_count; w++)
39 out[i++] = (uint8_t)(words[w] >> 8);
40 out[i++] = (uint8_t)words[w];
42 uint16_t crc = pc_interbus_fcs(out, i);
43 out[i++] = (uint8_t)(crc >> 8);
44 out[i++] = (uint8_t)crc;
48bool pc_interbus_parse(
const uint8_t *frame,
size_t len, uint16_t *out_words,
size_t max_words,
size_t *out_count)
50 if (!frame || !out_words || !out_count || len < 4)
54 if (((frame[0] << 8) | frame[1]) != PC_INTERBUS_LOOPBACK)
58 if ((len - 4) % 2 != 0)
62 size_t word_count = (len - 4) / 2;
63 if (word_count > max_words)
67 uint16_t want = pc_interbus_fcs(frame, len - 2);
68 uint16_t got = (uint16_t)((frame[len - 2] << 8) | frame[len - 1]);
73 for (
size_t w = 0; w < word_count; w++)
75 out_words[w] = (uint16_t)((frame[2 + w * 2] << 8) | frame[2 + w * 2 + 1]);
77 *out_count = word_count;
Parameterized CRC engine - one source of truth for every cyclic redundancy check.
constexpr pc_crc_params PC_CRC16_IBM_3740
CRC-16/IBM-3740 (often called CCITT-FALSE). check = 0x29B1.
uint32_t pc_crc(const pc_crc_params *p, const uint8_t *data, size_t len)
One-shot CRC of len octets at data.
INTERBUS summation-frame fieldbus codec (PC_ENABLE_INTERBUS).