ソースを参照

Receiving Toshiba is working and done. Chksum test.

Thomas Chef 2 年 前
コミット
9ea0a98d6e
3 ファイル変更70 行追加46 行削除
  1. 11 2
      main/receiver.c
  2. 32 17
      main/toshiba_ir.c
  3. 27 27
      main/toshiba_ir.h

+ 11 - 2
main/receiver.c

@@ -24,6 +24,7 @@ uint32_t dataArr[1000];
 uint32_t dataArrIdx = 0;
 
 
+
 void receiverTask(void *pvParameter)
 {
     ESP_LOGI("RX", "Receiver task starting.");
@@ -34,13 +35,21 @@ void receiverTask(void *pvParameter)
 
         while( xQueueReceive( rxQueue, &width, portMAX_DELAY ) == pdTRUE ) {
 
-            ESP_LOGI("D", "%u", width);
+            //ESP_LOGI("D", "%u", width);
 
             // Receive the Toshiba IR
             union ToshibaProtocolU* data = (union ToshibaProtocolU*)nextPulseToshiba_ir(width);
             if( data != NULL ) {
 
-                ESP_LOGI("TOSHIBA", "Data: %02X %02X %02X %02X %02X %02X %02X %02X %02X",data->raw[8],data->raw[7],data->raw[6],data->raw[5],data->raw[4],data->raw[3],data->raw[2],data->raw[1],data->raw[0]);
+                char mqtt_s[50];
+                sprintf(mqtt_s,"%02X%02X%02X%02X%02X%02X%02X%02X%02X",data->raw[0],data->raw[1],data->raw[2],data->raw[3],data->raw[4],data->raw[5],data->raw[6],data->raw[7],data->raw[8]);
+                ESP_LOGI("TOSHIBA","MQTT: %s", mqtt_s);
+
+#ifdef MQTT_ENABLED
+                sendMQTTMessage("hall/ac/ir_cmd_rx", mqtt_s);
+#endif
+
+                ESP_LOGI("TOSHIBA", "Data: %02X %02X %02X %02X %02X %02X %02X %02X %02X",data->raw[0],data->raw[1],data->raw[2],data->raw[3],data->raw[4],data->raw[5],data->raw[6],data->raw[7],data->raw[8]);
 
                 const uint8_t fan = (data->data.Fan > 0) ? data->data.Fan-1 : data->data.Fan;
                 const uint8_t power = (data->data.Mode == 3) ? 1 : 0;

+ 32 - 17
main/toshiba_ir.c

@@ -5,6 +5,8 @@
 #include "rxTimer.h"
 #include <string.h>
 
+uint8_t xorBytes(const uint8_t * const start, const uint16_t length);
+
 /**
  * @Analys of Toshiba IR Rx:
  *  0  1  2  3  4  5  6  7  8
@@ -60,7 +62,7 @@ static uint32_t rx_numBits;
 void Toshiba_ir_ResetDecoder()
 {
     //ESP_LOGI("T", "Reset decoder");
-    rx_numBits = kToshibaNumberOfBits;
+    rx_numBits = 0;
     rx_state = UNKNOWN;
     memset(data,0,kToshibaNumberOfBytes);
 }
@@ -69,17 +71,15 @@ static void addBit(uint8_t value)
 {
     if( value == 1 ) {
 
+        const uint8_t byteNo = rx_numBits / 8;
+        const uint8_t shiftBits = rx_numBits % 8;
 
-        const uint8_t byteNo = (rx_numBits+7) / 8;
-        const uint8_t shiftBits = (int)rx_numBits - (byteNo*8) + 7;
-
-    //ESP_LOGI("BIT RX:","%u  %u", byteNo, shiftBits);
+        //ESP_LOGI("BIT RX:","%u  %u", byteNo, shiftBits);
 
-
-        data[byteNo-1] |= ((uint8_t)1u) << shiftBits;
+        data[byteNo] |= 1u << (7-shiftBits);
     }
 
-    rx_numBits--;
+    rx_numBits++;
 }
 
 #define START_PULSE_MIN (kToshibaAcHdrMark-200)
@@ -125,14 +125,10 @@ static int32_t rx_decode(uint32_t width)
 
         case T0: // First half of pulse : HIGH around 230us
 
-            if(rx_numBits == 0)
+            if(rx_numBits == kToshibaNumberOfBits)
             { // end of frame
                 //ESP_LOGI("T", "END OF FRAME");
                 rx_state = DONE;
-
-                /*for(uint8_t i=9; i>0 ;i--) {
-                    ESP_LOGI("DATA","Byte %u   :  %02x", i-1, data[i-1]);
-                }*/
                 return 1;
             }
             else if( T0_PULSE_MIN <= width && width <= T0_PULSE_MAX )
@@ -184,13 +180,32 @@ uint8_t* nextPulseToshiba_ir(uint32_t width)
                 break;
             case 1:
                 rx_state = DONE;
-                memcpy(dataTransfer,data,kToshibaNumberOfBytes);
-                Toshiba_ir_ResetDecoder();
-                retVal = dataTransfer;
+                // Check checksum
+                if( xorBytes(data,8) == data[8] ) {
+                    memcpy(dataTransfer,data,kToshibaNumberOfBytes);
+                    Toshiba_ir_ResetDecoder();
+                    retVal = dataTransfer;
+                }
+                else {
+                    ESP_LOGE("TOSHIBA", "WRONG CHKSUM");
+                    Toshiba_ir_ResetDecoder();
+                }
                 break;
             }
         }
     }
     
     return retVal;
-}
+}
+
+/// Calculate a rolling XOR of all the bytes of an array.
+/// @param[in] start A ptr to the start of the byte array to calculate over.
+/// @param[in] length How many bytes to use in the calculation.
+/// @return The 8-bit calculated result of all the bytes and init value.
+/// Copied from: https://github.com/crankyoldgit/IRremoteESP8266/blob/master/src/IRutils.cpp
+uint8_t xorBytes(const uint8_t * const start, const uint16_t length) {
+  uint8_t checksum = 0;
+  const uint8_t *ptr;
+  for (ptr = start; ptr - start < length; ptr++) checksum ^= *ptr;
+  return checksum;
+}

+ 27 - 27
main/toshiba_ir.h

@@ -12,40 +12,40 @@ uint8_t* nextPulseToshiba_ir(uint32_t width);
 #define kToshibaNumberOfBytes (kToshibaNumberOfBits/8)
 
 struct toshibaDataBits {
-    // Byte[8]
-    // (Checksum for 72 bit messages, Eco/Turbo for long 80 bit messages)
-    uint8_t EcoTurbo :8;
-    // Byte[7]
-    uint8_t          :4;
-    uint8_t Filter   :1;
+    // Byte[0] - 0xF2
+    uint8_t :8;
+    // Byte[1] - 0x0D (inverted previous byte's value)
+    uint8_t :8;
+    // Byte[2] - The expected payload length (in bytes) past the Byte[4].
+    ///< Known lengths are:
+    ///<   1 (56 bit message)
+    ///<   3 (72 bit message)
+    ///<   4 (80 bit message)
+    uint8_t Length   :8;
+    // Byte[3] - The bit-inverted value of the "length" byte.
+    uint8_t          :8;
+    // Byte[4]
     uint8_t          :3;
-    // Byte[6]
-    uint8_t Mode     :3;
+    uint8_t LongMsg  :1;
+    uint8_t          :1;
+    uint8_t ShortMsg :1;
     uint8_t          :2;
-    uint8_t Fan      :3;
     // Byte[5]
     uint8_t Swing    :3;
     uint8_t          :1;
     uint8_t Temp     :4;
-    // Byte[4]
-    uint8_t          :3;
-    uint8_t LongMsg  :1;
-    uint8_t          :1;
-    uint8_t ShortMsg :1;
+    // Byte[6]
+    uint8_t Mode     :3;
     uint8_t          :2;
-    // Byte[3] - The bit-inverted value of the "length" byte.
-    uint8_t          :8;
-    // Byte[2] - The expected payload length (in bytes) past the Byte[4].
-    ///< Known lengths are:
-    ///<   1 (56 bit message)
-    ///<   3 (72 bit message)
-    ///<   4 (80 bit message)
-    uint8_t Length   :8;
-    // Byte[1] - 0x0D (inverted previous byte's value)
-    uint8_t :8;
-    // Byte[0] - 0xF2
-    uint8_t StartByte :8;
-    
+    uint8_t Fan      :3;
+    // Byte[7]
+    uint8_t          :4;
+    uint8_t Filter   :1;
+    uint8_t          :3;
+
+    // Byte[8]
+    // (Checksum for 72 bit messages, Eco/Turbo for long 80 bit messages)
+    uint8_t EcoTurbo :8;
 };