Контрольная сумма пакетов

Тема в разделе "Arduino & Shields", создана пользователем Un_ka, 20 янв 2019.

  1. Un_ka

    Un_ka Гуру

    Для ик передачи решил подстраховаться хеш-сумой.
    Сделал это потому что при многократном нажатии кнопки пульта, появлялись переполнения или левые( а может быть правые ) значения.
    Вся информация раскладывается по разрядам миллиарда
    Последние два разряда это сумма всех остальных разрядов.
    Как счистите , насколько годный метод?
    Кстати , у меня отправка работала только при такой конфигурации:
    Код (C++):
    irsend.sendJVC(val, 32, 0);
     
    В примере вместо 32 было либо 16 либо sizeOf одного числа делилось на sizeOf другого
    Ставил sizeof -не прокатывает...
     
  2. Un_ka

    Un_ka Гуру

    Как вам мой способ передачи сигналов управления:
    ......серво
    .........../ .. \
    ......верт горизонт
    .........|....|
    ..1‘180‘180‘5‘24}------ сумма
    ..|..............|
    ..фары.......режим
    .................моторов
     
  3. asam

    asam Гик

    Зачем изобретать велосипед если есть старый, добрый CRC? В зависимости от длины пакета выбирается CRC8 или СRС16
     
  4. Un_ka

    Un_ka Гуру

    Вот скетчи всего этого дела :
    Код (C++):
    #include <RCSwitch.h>
    RCSwitch mySwitch = RCSwitch();
    #include "IRremote.h"
    IRrecv irrecv(8);
    decode_results results;
    #include <Servo.h>
    #define in1  3
    #define in2  4
    #define in3  5
    #define in4  6
    Servo servoV;//вертикаль
    Servo servoRul;
    byte code[9] = {};
    bool laser = 0, istbit=0;
    int i ;
    byte led = 1, stat = 0,Gsum=0;
    volatile unsigned long st=0;
    unsigned long agra,val,has,digit;
    void setup() {
      Serial.begin(9600);
      Serial.print("startyem");
      pinMode(in1, OUTPUT);
      pinMode(in2, OUTPUT);
      pinMode(in3, OUTPUT);
      pinMode(in4, OUTPUT);
      servoV.attach(9);
      servoRul.attach(10);
      pinMode(7, OUTPUT);
      pinMode(13, OUTPUT);
      attachInterrupt(0, wall, FALLING);
      mySwitch.enableTransmit(10);
      irrecv.enableIRIn();


    }
    void loop() {
      if (irrecv.decode( &results )) {
        Serial.println(results.value, DEC);
        if (stat == 0 || stat == 1) {
          agra = results.value; //
          hash(agra);
          if (istbit == 1) {
            switch (code[2]) {
              case 0:
                ostanovka();
                break;
              case 1: go();
                break;        //go
              case 2: back();
                break;        //back
              case 3: left();
                break;        //left
              case 4: rihgt();
                break;        //right

            }
            code[0] = ( (code[8] * 100) + (code[7] * 10) + code[6]);
            if (servoV.read() != code[0]) {
              servoV.write(code[0]);
            }
            code[0] = ( (code[5] * 100) + (code[4] * 10) + code[3]);
            if (servoRul.read() != code[0]) {
              servoRul.write(code[0]);
            }
            switch (code[9]) {
              case 1:
                digitalWrite( 7, 1 );
                led = 2;
                break;
              case 2:
                digitalWrite( 7, 0 );
                led = 1;
                break;
            }
          }
        }
      }
    }
    void hash(unsigned long val) {
      has = val / 100;
      has = val - (has * 100);
      for (int d = 9; d--; d >= 2) {
        digit = val / pow(10, d);
        code[d] = digit;
        Gsum += digit;
        int e = digit * pow(10, d);
        val -= e;
      } if (has == Gsum || stat == 1) {
        istbit = 1;
      }
    }

    void wall() {
      if (st < millis() - 1000) {
        //back();
        //delay(5);
        ostanovka();
        st = millis();
      }}
      void ostanovka() {
        digitalWrite( A0, 0 );
        digitalWrite( A1, 0 );
        digitalWrite( A2, 0 );
        digitalWrite( A3, 0 );
      }
      void go() {
        digitalWrite( A0, 0 );
        digitalWrite( A1, 1 );
        digitalWrite( A2, 0 );
        digitalWrite( A3, 1 );
      }
      void back() {
        digitalWrite( A0, 1 );
        digitalWrite( A1, 0 );
        digitalWrite( A2, 1 );
        digitalWrite( A3, 0 );
      }
      void left() {
        digitalWrite( A0, 1 );
        digitalWrite( A1, 0 );
        digitalWrite( A2, 0 );
        digitalWrite( A3, 1 );
      }
      void rihgt() {
        digitalWrite( A0, 0 );
        digitalWrite( A1, 1 );
        digitalWrite( A2, 1 );
        digitalWrite( A3, 0 );
      }
     
    Код (C++):
    #include <RCSwitch.h>
    RCSwitch mySwitch = RCSwitch();
    #include <IRremote.h>
    IRsend irsend;
    bool tig = 0 ;
    unsigned long agra, timer_per = 0, zajat_timerV = 0, zajat_timerG = 0;
    unsigned long per = 100;
    volatile unsigned long last_timer = 0;
    volatile byte state_key = 1
    byte reader ;
    int vert, gor, pribavka, reade, digit;
    byte Gsum, mot ;
    void setup() {
      Serial.begin(9600);
      Serial.print("Mao niao");
      attachInterrupt(0, status_key, FALLING);
      pinMode( 2, OUTPUT );
      mySwitch.enableReceive(12);
      if (digitalRead(4) == 1) {
        tig = 1;
      }
    }
    void loop() {
      if ( millis()-timer_per>per) {
        Gsum = 0;
        agra = (unsigned long)state_key * 1000000000;

        Gsum += state_key;
        reade = analogRead(A0);
        if (zajat_timerV + (5 * per) > millis()) {
          pribavka = 3;
        }

        //--------вертикаль-----------
        if (reade < 900) {
          pribavka = -1 * abs(pribavka);
          zajat_timerV = millis();
        } else if (reade > 2100) {
          pribavka = abs(pribavka);
          zajat_timerV = millis();
        } else {
          pribavka = 0;
        }
        vert += pribavka;
        vert = constrain(vert, 0, 180);
        agra = (unsigned long)agra + (vert * 1000000);

        servo_hash(vert);

        //GORIZONT
        reade = analogRead(A1);
        if (zajat_timerG + (5 * per) > millis()) {
          pribavka = 3;
        }
        if (reade < 900) {
          pribavka = -1 * abs(pribavka);
          zajat_timerG = millis();
        } else if (reade > 2100) {
          pribavka = abs(pribavka);
          zajat_timerG = millis();
        } else {
          pribavka = 0;
        }
        gor = gor + pribavka;
        gor = constrain(gor, 0, 180);
        agra = (unsigned long) agra + (gor * 1000);
        servo_hash(gor);
        //Motors

        reade = analogRead(A3);
        if (reade < 900) {
          mot = 3;
        } else if (reade > 2100) {
          mot = 4;
        } else {
          mot = 0; //stop
        }

        reade = analogRead(A2);
        if (reade < 900) {
          mot = 1; //go
        } else if (reade > 2100) {
          mot = 2; //back
        } else {
          mot = 0; //stop
        }
        Gsum += mot;
        agra = (unsigned long)agra + (mot * 100);
        agra = (unsigned long)agra + Gsum;
        Serial.println(agra, DEC);
        Serial.println(Gsum, DEC);
        irsend.sendJVC(agra, 32, 0); // hex value, 16 bits, repeat
        delay(50);
        /* if(tig==1){
          if( mySwitch.available() ){
              int value = mySwitch.getReceivedValue();

              if( value == B1000 ){
                  digitalWrite( 13, HIGH );
              }else if( value == B0100 ){
                  digitalWrite( 13, LOW );
              }
              mySwitch.resetAvailable();
          }
          }*/

        timer_per = millis();
      }
    }
    void servo_hash(int val) {
      for (int d = 2; d--; d >= 0) {
        digit = (val / pow(10, d));
        Gsum = Gsum + digit;
        int e = (digit * pow(10, d)) ;
        val -= e;
      }
    }
    void status_key() {
      if ((last_timer + (per / 2)) < millis()) {
        switch (state_key) {
          case 1: state_key = 2; break;
          case 2: state_key = 1; break;
        }
        last_timer = millis();
      }
    }
     
     
  5. Un_ka

    Un_ka Гуру