#pragma once #include #define IRDEBUG_INFO /*////////////////////////////////////////////////////////////////////////////////////// Для работы в паре положить декодер в энкодер */// Адресация с 1 до 65 499 #define IR_Broadcast 65000 // 65 500 ~ 65 535 - широковещательные пакеты (всем), возможно разделить на 35 типов /* Адрес 0 запрещен и зарезервирован под NULL, либо тесты IR_MSG_ACCEPT с адреса 0 воспринимается всеми устройствами Адресное пространство: Излучатели контрольных точек: 1000 ~ 1999 Излучатели без обратной связиЖ 2000 ~ 2999 Излучатели светофоров: 3000 ~ 3999 /```````````````````````````````````````````````` data pack `````````````````````````````````````````````\                                                                                                                                             {``````````} [````````````````````````] [````````````````````] [````````````````````````] [``````````````] { msg type } [ addr_from uint16_t ] [ addr_to uint16_t ] [====== data bytes ======] [ CRC Bytes ] {..........} [........................] [....................] [........................] [..............]                                                                                                            { aka size } [addr_from_H][addr_from_L] [addr_to_H][addr_to_L] [data_H][data_n..][data_L] [ crc1 ][ crc2 ] |     0           1            2              3         4          5                         |       |     \____________________________________________________________________________________________/       |     |                                                                                                    |     \____________________________________________________________________________________________________/     msg type:                                         //  __________                                         // | 01234567 |                                         //  ----------                                         // | xxx..... | = тип сообщения                                         // | ...xxxxx | = длина (максимум 31 бита)                                         //  ---------- */ #define IR_MSG_BACK 0U // | 000...... | = Задний сигнал машинки #define IR_MSG_ACCEPT 1U // | 001..... | = подтверждение #define IR_MSG_REQUEST 2U // | 010..... | = запрос #define IR_MSG_ 3U // | 011..... | = ?? #define IR_MSG_BACK_TO 4U // | 100..... | = Задний сигнал машинки c адресацией #define IR_MSG_ 5U // | 101..... | = ?? #define IR_MSG_DATA_NOACCEPT 6U // | 110..... | = данные, не требующие подтверждения #define IR_MSG_DATA_ACCEPT 7U // | 111..... | = данные требующие подтверждения ;/*   // ---------- /```````````````````` подтверждение ```````````````````\      /``````````````````````````````````````` запрос ``````````````````````````````````\                                                                                                                        {``````````} [````````````````````````] [``````````````````] [``````````````]      {``````````} [````````````````````````] [````````````````````````] [``````````````] { msg type } [ addr_from uint16_t ] [=== customByte ===] [ CRC Bytes ]      { msg type } [ addr_from uint16_t ] [ addr_to uint16_t ] [ CRC Bytes ] {..........} [........................] [..................] [..............]      {..........} [........................] [........................] [..............]                                                                                                                                                              { 001..... } [addr_from_H][addr_from_L] [=== customByte ===] [ crc1 ][ crc2 ]      { 010..... } [addr_from_H][addr_from_L] [addr_from_H][addr_from_L] [ crc1 ][ crc2 ] |     0            1           2                  3              4       5          |     0            1           2              3           4           5       6     \________________________________________________________________/       |          \_____________________________________________________________________/       |     |                                                                        |          |                                                                             |     \________________________________________________________________________/          \_____________________________________________________________________________/     /`````````````````````` Задний сигнал машинки без адресации ``````````````````````\        В (IR_MASK_MSG_INFO & 15U) содержится количество байт                                                                                            сквозных команд, максимум 15 {``````````} [````````````````````````] [````````````````````````] [``````````````]        Если полезных байт информации нет, отправляется один { msg type } [ addr_from uint16_t ] [====== data bytes ======] [ CRC Bytes ]        байт нулей {..........} [........................] [........................] [..............]                                                                                                     { 0000xxxx } [addr_from_H][addr_from_L] [data_H][data_n..][data_L] [ crc1 ][ crc2 ]         |     0           1            2            3                         |       |             \_____________________________________________________________________/       |             |                                                                             |             \_____________________________________________________________________________/             /```````````````````````````````````` Задний сигнал машинки с адресацией ````````````````````````````````````\                                                                                       {``````````} [````````````````````````] [````````````````````````] [````````````````````````] [``````````````]  { msg type } [ addr_from uint16_t ] [ addr_to uint16_t ] [====== data bytes ======] [ CRC Bytes ]  {..........} [........................] [........................] [........................] [..............]                                                                                                                  { 0001xxxx } [addr_from_H][addr_from_L] [addr_from_H][addr_from_L] [data_H][data_n..][data_L] [ crc1 ][ crc2 ]  |     0           1            2              3           4            5                         |       |      \________________________________________________________________________________________________/       |      |                                                                                                        |      \________________________________________________________________________________________________________/      */ #define IR_MASK_MSG_TYPE 0b00000111 #define IR_MASK_MSG_INFO 0b00011111 /* /////////////////////////////////////////////////////////////////////////////////////*/ typedef uint16_t crc_t; #define bytePerPack 16 // колличество байтов в пакете #ifndef freeFrec #define freeFrec true #endif #define subBufferSize 15 //Буфер для складирования фронтов, пока их не обработают (передатчик) #define preambPulse 3 #define disablePairDec false // Отключать парный приёмник, возможны баги, используйте setBlindDecoders() ///////////////////////////////////////////////////////////////////////////////////// #define bitPerByte 8U // Колличество бит в байте #define addrBytes 2 #define msgBytes 1 #define crcBytes 2 #define poly1 0x31 #define poly2 0x8C #define syncBits 3U // количество битов синхронизации #define dataByteSizeMax (msgBytes + addrBytes + addrBytes + bytePerPack + crcBytes) #define preambFronts (preambPulse*2) // количество фронтов преамбулы (Приём) #define preambToggle ((bitPauseTakts * 2 + bitActiveTakts) * 2 - 1) // колличество переключений преамбулы (Передача) #define carrierFrec 38000U // частота несущей (Приём/Передача) #define carrierPeriod (1000000U/carrierFrec) // период несущей в us (Приём) // В процессе работы значения будут отклонятся в соответствии с предыдущим битом #define bitActiveTakts 25U // длительность высокого уровня в тактах #define bitPauseTakts 6U // длительность низкого уровня в тактах #define bitTakts (bitActiveTakts+(bitPauseTakts*2U)) // Общая длительность бита в тактах #define bitTime (bitTakts*carrierPeriod) // Общая длительность бита #define tolerance 300U class IR_FOX { public: struct PackOffsets { uint8_t msgOffset; uint8_t addrFromOffset; uint8_t addrToOffset; uint8_t dataOffset; uint8_t crcOffset; }; struct ErrorsStruct { uint8_t lowSignal = 0; uint8_t highSignal = 0; uint8_t other = 0; void reset() { lowSignal = 0; highSignal = 0; other = 0; } uint16_t all() { return lowSignal + highSignal + other; } }; struct PackInfo { uint8_t* buffer = nullptr; uint8_t packSize = 0; uint16_t crc = 0; ErrorsStruct err; uint16_t rTime = 0; }; static void checkaddressRuleApply(uint16_t address, uint16_t id, bool& flag) { flag = false; flag |= id == 0; flag |= address == id; flag |= address >= IR_Broadcast; } protected: ErrorsStruct errors; uint8_t crc8(uint8_t* data, uint8_t start, uint8_t end, uint8_t poly) { //TODO: сделать возможность межбайтовой проверки uint8_t crc = 0xff; size_t i, j; for (i = start; i < end; i++) { crc ^= data[i]; for (j = 0; j < 8; j++) { if ((crc & 0x80) != 0) crc = (uint8_t)((crc << 1) ^ poly); else crc <<= 1; } } return crc; } };