diff --git a/.gitignore b/.gitignore index 67b8ef7..8172f79 100644 --- a/.gitignore +++ b/.gitignore @@ -1,4 +1,5 @@ .vscode/* bin/* !.vscode/arduino.json -!.vscode/launch.json \ No newline at end of file +!.vscode/launch.json +log/* \ No newline at end of file diff --git a/.vscode/arduino.json b/.vscode/arduino.json index 7c70ba3..fb0e740 100644 --- a/.vscode/arduino.json +++ b/.vscode/arduino.json @@ -1,6 +1,6 @@ { - "configuration": "device_variant=STM32F103C8,upload_method=STLinkMethod,cpu_speed=speed_72mhz,opt=osstd", - "board": "stm32duino:STM32F1:genericSTM32F103C", + "configuration": "pnum=BLUEPILL_F103C8,upload_method=swdMethod,xserial=none,usb=CDCgen,xusb=FS,opt=osstd,dbg=none,rtlib=nano", + "board": "STMicroelectronics:stm32:GenF1", "port": "COM17", "output": "bin", "prebuild": "if exist bin rd /s /q bin", diff --git a/IR-protocol.ino b/IR-protocol.ino index 3520824..2a1f9a7 100644 --- a/IR-protocol.ino +++ b/IR-protocol.ino @@ -72,7 +72,6 @@ uint8_t data4[] = {42, 127, 137, 255}; uint32_t loopTimer; uint8_t sig = 0; - uint16_t targetAddr = IR_Broadcast; Timer t1(500, millis, []() { @@ -157,17 +156,24 @@ Timer t1(500, millis, []() // encBackward.sendData(IR_Broadcast, data2); // encTree.sendData(IR_Broadcast, rawData3); }); -Timer t2(500, millis, []() - { digitalToggle(LED_BUILTIN); }); +// Timer t2(50, millis, []() +// { digitalToggle(LED_BUILTIN); }); Timer signalDetectTimer; ///////////////////////////////////////////////////////////////////// +HardwareTimer IR_Timer(TIM3); +HardwareTimer MicrosTimer(TIM1); + +void MicrosTimerISR(){ + +} + void setup() { - // disableDebugPorts(); + // MicrosTimer.setOve - Timer3.setPeriod(1000000U / carrierFrec / 2); - // Timer3.attachCompare1Interrupt(EncoderISR); + IR_Timer.setOverflow(carrierFrec*2, HERTZ_FORMAT); + IR_Timer.attachInterrupt(1, EncoderISR); Serial.begin(SERIAL_SPEED); @@ -276,7 +282,7 @@ void status(IR_Decoder &dec) // str += (" CRC CALC: "); str += (dec.gotData.getCrcCALC()); str += "\n"; str += "\n"; - for (size_t i = 0; i < min(10, dec.gotData.getDataSize()); i++) + for (size_t i = 0; i < min(uint8_t(10), dec.gotData.getDataSize()); i++) { switch (i) { @@ -348,7 +354,7 @@ void status(IR_Decoder &dec) // str += (" CRC CALC: "); str += (dec.gotBackData.getCrcCALC()); str += "\n"; str += "\n"; - for (size_t i = 0; i < min(10, dec.gotBackData.getDataSize()); i++) + for (size_t i = 0; i < min(uint8_t(10), dec.gotBackData.getDataSize()); i++) { switch (i) { diff --git a/IR_DecoderRaw.cpp b/IR_DecoderRaw.cpp index 43dcc0c..6fdae21 100644 --- a/IR_DecoderRaw.cpp +++ b/IR_DecoderRaw.cpp @@ -15,55 +15,47 @@ IR_DecoderRaw::IR_DecoderRaw(const uint8_t isrPin, uint16_t addr, IR_Encoder *en pinMode(wrLow, OUTPUT); pinMode(writeOp, OUTPUT); pinMode(errOut, OUTPUT); + pinMode(up, OUTPUT); + pinMode(down, OUTPUT); #endif } //////////////////////////////////// isr /////////////////////////////////////////// +volatile uint32_t time_; void IR_DecoderRaw::isr() { - if (isPairSending) - return; - - subBuffer[currentSubBufferIndex].next = nullptr; - subBuffer[currentSubBufferIndex].dir = digitalRead(isrPin); - subBuffer[currentSubBufferIndex].time = micros(); - - if (firstUnHandledFront == nullptr) + noInterrupts(); + // time_ = HAL_GetTick() * 1000 + ((SysTick->LOAD + 1 - SysTick->VAL) * 1000) / SysTick->LOAD + 1; + time_ = micros(); + interrupts(); + if (time_ < oldTime) { - firstUnHandledFront = &subBuffer[currentSubBufferIndex]; // Если нет необработанных данных - добавляем их - isSubBufferOverflow = false; - } - else - { - if (firstUnHandledFront == &subBuffer[currentSubBufferIndex]) - { // Если контроллер не успел обработать новый сигнал, принудительно пропускаем его - firstUnHandledFront = firstUnHandledFront->next; - isSubBufferOverflow = true; - -#ifdef IRDEBUG_INFO - // Serial.println(); - Serial.println(" ISR BUFFER OVERFLOW "); -// Serial.println(); +#ifdef IRDEBUG + Serial.print("\n"); + Serial.print("count: "); + Serial.println(wrongCounter++); + Serial.print("time: "); + Serial.println(time_); + Serial.print("oldTime: "); + Serial.println(oldTime); + Serial.print("sub: "); + Serial.println(max((uint32_t)time_, oldTime) - min((uint32_t)time_, oldTime)); #endif - } + time_ += 1000; } + oldTime = time_; - if (lastFront == nullptr) - { - lastFront = &subBuffer[currentSubBufferIndex]; - } - else - { - lastFront->next = &subBuffer[currentSubBufferIndex]; - lastFront = &subBuffer[currentSubBufferIndex]; - } + FrontStorage edge; + edge.dir = digitalRead(isrPin); + edge.time = time_; - currentSubBufferIndex == (subBufferSize - 1) ? currentSubBufferIndex = 0 : currentSubBufferIndex++; // Закольцовка буффера + subBuffer.push(edge); } //////////////////////////////////////////////////////////////////////////////////// +uint32_t wrCounter; void IR_DecoderRaw::firstRX() { @@ -86,6 +78,8 @@ void IR_DecoderRaw::firstRX() isPreamb = true; riseSyncTime = bitTime /* 1100 */; + wrCounter = 0; + memset(dataBuffer, 0x00, dataByteSizeMax); } @@ -98,56 +92,116 @@ void IR_DecoderRaw::listenStart() firstRX(); } } - void IR_DecoderRaw::tick() { FrontStorage currentFront; noInterrupts(); listenStart(); - if (firstUnHandledFront == nullptr) + FrontStorage *currentFrontPtr; + currentFrontPtr = subBuffer.pop(); + if (currentFrontPtr == nullptr) { isSubBufferOverflow = false; interrupts(); return; - } // Если данных нет - ничего не делаем - currentFront = *((FrontStorage *)firstUnHandledFront); // найти следующий необработанный фронт/спад + } // Если данных нет - ничего не делаем + currentFront = *currentFrontPtr; interrupts(); - if (currentFront.next == nullptr) - { - isRecive = false; - return; - } + //////////////////////////////////////////////////////////////////////////////////////////////////////////// + if (currentFront.dir) + { // Если __/``` ↑ + if (currentFront.time - prevRise > riseTimeMax / 2 || highCount || lowCount) + { // комплексный фикс рваной единицы + risePeriod = currentFront.time - prevRise; + highTime = currentFront.time - prevFall; + lowTime = prevFall - prevRise; + prevRise = currentFront.time; + + if ( + risePeriod > UINT32_MAX - IR_timeout * 10 || + highTime > UINT32_MAX - IR_timeout * 10 || + lowTime > UINT32_MAX - IR_timeout * 10 || + prevRise > UINT32_MAX - IR_timeout * 10) + { +#ifdef IRDEBUG + errPulse(down, 50); + + // Serial.print("\n"); + + // Serial.print("risePeriod: "); + // Serial.println(risePeriod); + + // Serial.print("highTime: "); + // Serial.println(highTime); + + // Serial.print("lowTime: "); + // Serial.println(lowTime); + + // Serial.print("prevRise: "); + // Serial.println(prevRise); +#endif + } + } + else + { + errors.other++; + } + } + else + { // Если ```\__ ↓ + + if (currentFront.time - prevFall > riseTimeMin / 4) + { + prevFall = currentFront.time; + } + else + { + errors.other++; + } + } +#ifdef IRDEBUG + // goto END; //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +#endif + //---------------------------------------------------------------------------------- +#ifdef IRDEBUG + digitalWrite(errOut, currentFront.dir); +#endif + if (currentFront.time > prevRise && currentFront.time - prevRise > IR_timeout * 2 && !isRecive) { // первый - preambFrontCounter = preambFronts - 1U; - - if (!currentFront.dir) - { -#ifdef IRDEBUG_INFO -// Serial.print(" currentFront.time: "); Serial.print(currentFront.time); -// Serial.print(" currentFront.dir: "); Serial.print(currentFront.dir ? "UP" : "DOWN"); -// Serial.print(" next: "); Serial.print(currentFront.next == nullptr); -// Serial.print(" prevRise: "); Serial.print(prevRise); -// Serial.print(" SUB: "); Serial.println(currentFront.time - prevRise); +#ifdef IRDEBUG + errPulse(up, 50); + errPulse(down, 50); + errPulse(up, 150); + errPulse(down, 150); #endif - isRecive = true; - isWrongPack = false; - } + preambFrontCounter = preambFronts - 1U; + isPreamb = true; + + isRecive = true; + isWrongPack = false; } + //------------------------------------------------------------------------------------------------------- + if (preambFrontCounter) { // в преамбуле - uint32_t risePeriod; - risePeriod = currentFront.time - prevRise; +#ifdef IRDEBUG + Serial.print("risePeriod: "); + Serial.println(risePeriod); +#endif if (currentFront.dir && risePeriod < IR_timeout) { // __/``` ↑ и мы в внутри пакета - if (risePeriod < riseTimeMin << 1) + if (risePeriod < riseTimeMin / 2) { // fix рваной единицы preambFrontCounter += 2; errors.other++; +#ifdef IRDEBUG + errPulse(down, 350); +#endif } else { @@ -168,194 +222,182 @@ void IR_DecoderRaw::tick() if (isPreamb) { // первый фронт после // gotTune.set(riseSyncTime); + isPreamb = false; +#ifdef IRDEBUG + errPulse(up, 50); + errPulse(down, 50); +#endif + prevRise += risePeriod / 2; + // prevRise = currentFront.time + riseTime; + goto END; } - isPreamb = false; } + + if (isPreamb) + { + goto END; + } + if (risePeriod > IR_timeout || isBufferOverflow || risePeriod < riseTimeMin || isWrongPack) + // ~Мы в пределах таймаута и буффер не переполнен и fix дроблёных единиц + { + goto END; + } + // определить направление фронта if (currentFront.dir) { // Если __/``` ↑ - - uint16_t risePeriod = currentFront.time - prevRise; - uint16_t highTime = currentFront.time - prevFall; - uint16_t lowTime = prevFall - prevRise; - - int8_t highCount = 0; - int8_t lowCount = 0; - int8_t allCount = 0; + highCount = 0; + lowCount = 0; + allCount = 0; bool invertErr = false; - - if (!isPreamb) - { - if (risePeriod < IR_timeout && !isBufferOverflow && risePeriod > riseTimeMin && !isWrongPack) - { - // Мы в пределах таймаута и буффер не переполнен и fix дроблёных единиц - - if (aroundRise(risePeriod)) - { // тактирование есть, сигнал хороший - без ошибок(?) - - if (highTime > riseTimeMin / 2U) - { // 1 #ifdef IRDEBUG - digitalWrite(wrHigh, 1); -#endif - writeToBuffer(HIGH); - } - else - { // 0 -#ifdef IRDEBUG - digitalWrite(wrLow, 1); -#endif - writeToBuffer(LOW); - } - } - else - { // пропущены такты! сигнал средний // ошибка пропуска - highCount = ceil_div(highTime, riseTime); // предполагаемое колличество HIGH битов - lowCount = ceil_div(lowTime, riseTime); // предполагаемое колличество LOW битов - allCount = ceil_div(risePeriod, riseTime); // предполагаемое колличество всего битов + Serial.print("\n"); - if (highCount == 0 && highTime > riseTime / 3) - { // fix короткой единицы (?)после пропуска нулей(?) - highCount++; - errors.other++; -#ifdef IRDEBUG - errPulse(errOut, 2); -#endif - } + Serial.print("wrCounter: "); + Serial.println(wrCounter++); - if (lowCount + highCount > allCount) - { // fix ошибочных сдвигов - if (lowCount > highCount) - { // Лишние нули - lowCount = allCount - highCount; - errors.lowSignal += lowCount; -#ifdef IRDEBUG - errPulse(errOut, 3); -#endif - } - else if (lowCount < highCount) - { // Лишние единицы - highCount = allCount - lowCount; - errors.highSignal += highCount; -#ifdef IRDEBUG - errPulse(errOut, 4); -#endif - // неизвестный случай Инверсит след бит или соседние - // Очень редко - // TODO: Отловить проверить - } - else if (lowCount == highCount) - { - invertErr = true; - // Serial.print("..."); - errors.other += allCount; - } - // errorCounter += allCount; - } + Serial.print("risePeriod: "); + Serial.println(risePeriod); - // errorCounter += allCount; - // errors.other+=allCount; - if (lowCount < highCount) - { - errors.highSignal += highCount; - } - else - { - errors.lowSignal += lowCount; - } + Serial.print("highTime: "); + Serial.println(highTime); -#ifdef IRDEBUG - errPulse(errOut, 1); + Serial.print("lowTime: "); + Serial.println(lowTime); #endif - for (int8_t i = 0; i < lowCount && 8 - i; i++) - { // отправка LOW битов, если есть - if (i == lowCount - 1 && invertErr) - { - invertErr = false; - writeToBuffer(!LOW); -#ifdef IRDEBUG - digitalWrite(wrLow, 1); -#endif - } - else - { - writeToBuffer(LOW); -#ifdef IRDEBUG - digitalWrite(wrLow, 1); -#endif - } - } + if (aroundRise(risePeriod)) + { // тактирование есть, сигнал хороший - без ошибок(?) - for (int8_t i = 0; i < highCount && 8 - i; i++) - { // отправка HIGH битов, если есть - if (i == highCount - 1 && invertErr) - { - invertErr = false; - writeToBuffer(!HIGH); + if (highTime > lowTime) + { // 1 #ifdef IRDEBUG - digitalWrite(wrLow, 1); + errPulse(wrHigh, 1); #endif - } - else - { - writeToBuffer(HIGH); + writeToBuffer(HIGH); + } + else + { // 0 #ifdef IRDEBUG - digitalWrite(wrHigh, 1); -#endif - } - } - } -#ifdef IRDEBUG - digitalWrite(wrHigh, 0); - digitalWrite(wrLow, 0); + errPulse(wrLow, 1); #endif + writeToBuffer(LOW); } } - if (risePeriod > riseTimeMax / 2 || highCount || lowCount) - { // комплексный фикс рваной единицы - prevPrevRise = prevRise; - prevRise = currentFront.time; - } else - { - errors.other++; + { // пропущены такты! сигнал средний // ошибка пропуска + highCount = ceil_div(highTime, riseTime); // предполагаемое колличество HIGH битов + lowCount = ceil_div(lowTime, riseTime); // предполагаемое колличество LOW битов + allCount = ceil_div(risePeriod, riseTime); // предполагаемое колличество всего битов + + if (highCount == 0 && highTime > riseTime / 3) + { // fix короткой единицы (?)после пропуска нулей(?) + highCount++; + errors.other++; #ifdef IRDEBUG - errPulse(errOut, 5); + errPulse(up, 50); #endif + } + + if (lowCount + highCount > allCount) + { // fix ошибочных сдвигов + if (lowCount > highCount) + { // Лишние нули + lowCount = allCount - highCount; + errors.lowSignal += lowCount; +#ifdef IRDEBUG + // errPulse(errOut, 3); + errPulse(down, 40); + errPulse(up, 10); + errPulse(down, 40); +#endif + } + else if (lowCount < highCount) + { // Лишние единицы + highCount = allCount - lowCount; + errors.highSignal += highCount; +#ifdef IRDEBUG + errPulse(down, 10); + errPulse(up, 40); + errPulse(down, 10); +// errPulse(errOut, 4); +#endif + // неизвестный случай Инверсит след бит или соседние + // Очень редко + // TODO: Отловить проверить + } + else if (lowCount == highCount) + { +#ifdef IRDEBUG + errPulse(down, 40); + errPulse(up, 40); + errPulse(down, 40); +#endif + invertErr = true; + // Serial.print("..."); + errors.other += allCount; + } + // errorCounter += allCount; + } + + // errorCounter += allCount; + // errors.other+=allCount; + if (lowCount < highCount) + { + errors.highSignal += highCount; + } + else + { + errors.lowSignal += lowCount; + } + + // errPulse(errOut, 1); + + for (int8_t i = 0; i < lowCount && 8 - i; i++) + { // отправка LOW битов, если есть + if (i == lowCount - 1 && invertErr) + { + invertErr = false; + writeToBuffer(HIGH); +#ifdef IRDEBUG + errPulse(wrHigh, 1); +#endif + } + else + { + writeToBuffer(LOW); +#ifdef IRDEBUG + errPulse(wrLow, 1); +#endif + } + } + + for (int8_t i = 0; i < highCount && 8 - i; i++) + { // отправка HIGH битов, если есть + if (i == highCount - 1 && invertErr) + { + invertErr = false; + writeToBuffer(LOW); +#ifdef IRDEBUG + errPulse(wrLow, 1); +#endif + } + else + { + writeToBuffer(HIGH); +#ifdef IRDEBUG + errPulse(wrHigh, 1); +#endif + } + } } } else { // Если ```\__ ↓ - - if (currentFront.time - prevFall > riseTimeMin) - { - prevPrevFall = prevFall; - prevFall = currentFront.time; - } - else - { -#ifdef IRDEBUG -// errPulse(errOut, 5); -#endif - } } - if (isPreamb && preambFrontCounter <= 0) - { - prevRise = currentFront.time + riseTime; - } - -#ifdef IRDEBUG - digitalWrite(writeOp, isPreamb); -#endif - //////////////////////////////////////////////////////////////////////////////////////////////////////////// - // noInterrupts(); - if (firstUnHandledFront != nullptr) - { - firstUnHandledFront = firstUnHandledFront->next; // переместить флаг на следующий элемент для обработки (next or nullptr) - } - // interrupts(); +//////////////////////////////////////////////////////////////////////////////////////////////////////////// +END:; } void IR_DecoderRaw::writeToBuffer(bool bit) @@ -484,7 +526,7 @@ void IR_DecoderRaw::writeToBuffer(bool bit) if (packSize && (i_dataBuffer == packSize * bitPerByte)) { // Конец #ifdef IRDEBUG_INFO - Serial.print(" END DATA "); + Serial.print(" END DATA " + crcCheck(packSize - crcBytes, crcValue) ? "OK " : "ERR "); #endif packInfo.buffer = dataBuffer; @@ -496,35 +538,33 @@ void IR_DecoderRaw::writeToBuffer(bool bit) isRecive = false; isAvailable = crcCheck(packSize - crcBytes, crcValue); - if (!isAvailable) // Исправление первого бита // Очень большая затычка... - for (size_t i = 0; i < packSize; ++i) - { - for (int j = 0; j < 8; ++j) +#ifdef BRUTEFORCE_CHECK + if (!isAvailable) // Исправление первого бита // Очень большая затычка... + for (size_t i = 0; i < min(packSize - crcBytes*2, dataByteSizeMax); ++i) { - // инвертируем бит - dataBuffer[i] ^= 1 << j; - - isAvailable = crcCheck(packSize - crcBytes, crcValue); - // обратно инвертируем бит в исходное состояние - - if (isAvailable) - { - #ifdef IRDEBUG_INFO - Serial.println("!!!INV!!!"); - #endif - goto OUT_BRUTEFORCE; - } - else + for (int j = 0; j < 8; ++j) { + // инвертируем бит dataBuffer[i] ^= 1 << j; + + isAvailable = crcCheck(packSize - crcBytes, crcValue); + // обратно инвертируем бит в исходное состояние + + if (isAvailable) + { + #ifdef IRDEBUG_INFO + Serial.println("!!!INV!!!"); + #endif + goto OUT_BRUTEFORCE; + } + else + { + dataBuffer[i] ^= 1 << j; + } } } - } - OUT_BRUTEFORCE:; - // { - // dataBuffer[0] |= 0b10000000; - // isAvailable = crcCheck(packSize - crcBytes, crcValue); - // } + OUT_BRUTEFORCE:; +#endif } } diff --git a/IR_DecoderRaw.h b/IR_DecoderRaw.h index 9e02c0a..de56567 100644 --- a/IR_DecoderRaw.h +++ b/IR_DecoderRaw.h @@ -1,7 +1,8 @@ #pragma once #include "IR_config.h" +#include "RingBuffer.h" -#define IRDEBUG +// #define IRDEBUG #ifdef IRDEBUG #define wrHigh PA1 // Запись HIGH инициирована // green @@ -10,7 +11,11 @@ // Исправленные ошибки // purle // 1 пульс: fix #define errOut PA4 +#define up PA3 +#define down PA2 #endif +#define up PA3 +#define down PA2 ///////////////////////////////////////////////////////////////////////////////////////////////// @@ -54,6 +59,7 @@ public: void isr(); // Функция прерывания void tick(); // Обработка приёмника, необходима для работы + void tickOld(); bool isOverflow() { return isBufferOverflow; }; // Буффер переполнился bool isSubOverflow() @@ -82,23 +88,38 @@ private: uint16_t riseSyncTime = bitTime; // Подстраиваемое время бита в мкс //////////////////////////////////////////////////////////////////////// - volatile uint8_t currentSubBufferIndex; // Счетчик текущей позиции во вспомогательном буфере фронтов/спадов + volatile uint32_t currentSubBufferIndex; // Счетчик текущей позиции во вспомогательном буфере фронтов/спадов struct FrontStorage - { // Структура для хранения времени и направления фронта/спада - volatile uint32_t time = 0; // Время - volatile bool dir = false; // Направление (true = ↑; false = ↓) - volatile FrontStorage *next = nullptr; // Указатель на следующий связанный фронт/спад, или nullptr если конец + { // Структура для хранения времени и направления фронта/спада + volatile uint32_t time = 0; // Время + volatile bool dir = false; // Направление (true = ↑; false = ↓) + // volatile FrontStorage *next = nullptr; // Указатель на следующий связанный фронт/спад, или nullptr если конец }; volatile FrontStorage *lastFront = nullptr; // Указатель последнего фронта/спада volatile FrontStorage *firstUnHandledFront = nullptr; // Указатель первого необработанного фронта/спада - volatile FrontStorage subBuffer[subBufferSize]; // вспомогательный буфер для хранения необработанных фронтов/спадов + // volatile FrontStorage subBuffer[subBufferSize]; // вспомогательный буфер для хранения необработанных фронтов/спадов + + RingBuffer subBuffer; + //////////////////////////////////////////////////////////////////////// - uint8_t dataBuffer[dataByteSizeMax]{0}; // Буффер данных - uint32_t prevRise, prevPrevRise, prevFall, prevPrevFall; // Время предыдущих фронтов/спадов - uint16_t errorCounter = 0; // Счётчик ошибок - int8_t preambFrontCounter = 0; // Счётчик __/``` ↑ преамбулы - int16_t bufBitPos = 0; // Позиция для записи бита в буффер + uint8_t dataBuffer[dataByteSizeMax]{0}; // Буффер данных + volatile uint32_t prevRise, prevPrevRise, prevFall, prevPrevFall; // Время предыдущих фронтов/спадов + + volatile uint32_t risePeriod; + volatile uint32_t highTime; + volatile uint32_t lowTime; + + uint32_t oldTime; + uint16_t wrongCounter; + + int8_t highCount; + int8_t lowCount; + int8_t allCount; + + uint16_t errorCounter = 0; // Счётчик ошибок + int8_t preambFrontCounter = 0; // Счётчик __/``` ↑ преамбулы + int16_t bufBitPos = 0; // Позиция для записи бита в буффер private: void listenStart(); // @brief Слушатель для работы isReciving() @@ -129,7 +150,7 @@ private: /// @return Результат uint16_t ceil_div(uint16_t val, uint16_t divider); -#ifdef IRDEBUG +#if true //def IRDEBUG inline void errPulse(uint8_t pin, uint8_t count); inline void infoPulse(uint8_t pin, uint8_t count); #endif diff --git a/IR_Encoder.cpp b/IR_Encoder.cpp index cfea755..f97d05d 100644 --- a/IR_Encoder.cpp +++ b/IR_Encoder.cpp @@ -160,7 +160,7 @@ void IR_Encoder::_sendBack(bool isAdressed, uint16_t addrTo, uint8_t *data, uint memset(sendBuffer, 0x00, dataByteSizeMax); uint8_t dataStart = msgBytes + addrBytes + (isAdressed ? addrBytes : 0); - uint8_t packSize = msgBytes + addrBytes + (isAdressed ? addrBytes : 0) + min(1, len) + crcBytes; + uint8_t packSize = msgBytes + addrBytes + (isAdressed ? addrBytes : 0) + min(uint8_t(1), len) + crcBytes; uint8_t msgType = ((isAdressed ? IR_MSG_BACK_TO : IR_MSG_BACK) << 5) | ((packSize) & (IR_MASK_MSG_INFO >> 1)); @@ -398,8 +398,8 @@ void IR_Encoder::send_EMPTY(uint8_t count) } uint8_t* IR_Encoder::bitHigh = new uint8_t[2]{ - (bitPauseTakts * 2) * 2 - 1, + (bitPauseTakts) * 2 - 1, (bitActiveTakts) * 2 - 1}; uint8_t* IR_Encoder::bitLow = new uint8_t[2]{ - (bitPauseTakts + bitActiveTakts) * 2 - 1, - (bitPauseTakts) * 2 - 1}; \ No newline at end of file + (bitPauseTakts/2 + bitActiveTakts) * 2 - 1, + (bitPauseTakts) - 1}; \ No newline at end of file diff --git a/IR_config.h b/IR_config.h index bf3053e..3935d62 100644 --- a/IR_config.h +++ b/IR_config.h @@ -101,13 +101,14 @@ customByte - контрольная сумма принятых данных п /////////////////////////////////////////////////////////////////////////////////////*/ typedef uint16_t crc_t; +// #define BRUTEFORCE_CHECK // Перепроверяет пакет на 1 битные ошибки //TODO: зависает #define bytePerPack 16 // колличество байтов в пакете #ifndef freeFrec #define freeFrec false #endif #ifndef subBufferSize -#define subBufferSize 11 //Буфер для складирования фронтов, пока их не обработают (передатчик) +#define subBufferSize 5 //Буфер для складирования фронтов, пока их не обработают (передатчик) #endif #define preambPulse 3 @@ -134,12 +135,11 @@ typedef uint16_t crc_t; // В процессе работы значения будут отклонятся в соответствии с предыдущим битом #define bitActiveTakts 25U // длительность высокого уровня в тактах -#define bitPauseTakts 6U // длительность низкого уровня в тактах +#define bitPauseTakts 12U // длительность низкого уровня в тактах -#define bitTakts (bitActiveTakts+(bitPauseTakts*2U)) // Общая длительность бита в тактах +#define bitTakts (bitActiveTakts+bitPauseTakts) // Общая длительность бита в тактах #define bitTime (bitTakts*carrierPeriod) // Общая длительность бита #define tolerance 300U - class IR_FOX { public: struct PackOffsets { diff --git a/RingBuffer.h b/RingBuffer.h new file mode 100644 index 0000000..4e23bfe --- /dev/null +++ b/RingBuffer.h @@ -0,0 +1,39 @@ +#pragma once +#include "Arduino.h" +template +class RingBuffer { +public: + RingBuffer() : start(0), end(0) {} + + bool isFull() const { + return ((end + 1) % BufferSize) == start; + } + + bool isEmpty() const { + return start == end; + } + + void push(T element) { + noInterrupts(); + if (!isFull()) { + data[end] = element; + end = (end + 1) % BufferSize; + } + interrupts(); + } + + T* pop() { + noInterrupts(); + T* value = nullptr; + if (!isEmpty()) { + value = &data[start]; + start = (start + 1) % BufferSize; + } + interrupts(); + return value; + } + +private: + T data[BufferSize]; + unsigned int start, end; +}; \ No newline at end of file