Проблема передачи данных по UART

Jacks_d
Offline
Зарегистрирован: 31.12.2011

Точно не уверен что сюда, но все же.

Передаю данные (коды кнопок (IRremote.h) Nano -> Mega и другие данные по своему протоколу Mega -> Nano) с аппаратного сиреала NANO v3 (скорее всего китайская, на 328) на аппаратный Mega RX3/TX3, естественно земля общая и скорости одинаковые, посли према у обеих сбрасываю буфер посредствам  Serial.flush(), обе питаются от ЮСБ, провод RX/TX витая пара(одна) сантиметров 12, земля идет отдельным проводом. 

В какойто случайный момент, Нано перестает отправлять данные на Мегу, видно как в мониторе так и специально подключенном светодиоде который реагирует софтово на принятие от пульта определенной команды. При этом Нано принимает данные от Меги и могласно скетчу их отрабатывает. Тожесамое и с Мегой, просто может перестать принимать, в мониторе от наны данные идут, светодиоды RX/TX моргают, а мега ничего на входе не видит, хотя спокойно ее скетч работает и данные передает на Нану. Лечится Ресетом, но зависимотси глюка не заметил, может и буквально сразу перестати передавати принимать, а может со временем. 

Раньше подобное было когда была одна мега и температура с нее передавалась в сиреал на комп,  за часов 8, могла пару раз перестать передавать, и через случайный промежуток времени опять начать передава данные.

Вот думаю может кто сталкивался чего полезного скажет, может подтянуть пины к нулю через 10 кОм?

maksim
Offline
Зарегистрирован: 12.02.2012

Для начала покажите, что заливаете в Нану и что заливаете в Мегу и желательно не кусками кода, а полностью оба скейтча.

Jacks_d
Offline
Зарегистрирован: 31.12.2011
#include <IRremote.h>
byte lastpos[16];
byte val[6];
byte inserial[37];
boolean inserialAP = 0;
int delayled = 3;
int ledPin3  = 3;
int ledPin5  = 5;
int ledPin6  = 6;
int ledPin9  = 9;

long DU;
int RECV_PIN = 11;
IRrecv irrecv(RECV_PIN);
decode_results results;
void setup()  
{
Serial.begin(57600);  
pinMode(ledPin3,  OUTPUT);
pinMode(ledPin5,  OUTPUT);
pinMode(ledPin6,  OUTPUT);
pinMode(ledPin9,  OUTPUT);
irrecv.enableIRIn();
}
void dump(decode_results *results) {
  int count = results->rawlen;}
void loop() 
{
 if(irrecv.decode(&results)) 
   {
    if(results.value != 4294967295)
      {DU=results.value;Serial.print(DU, HEX);}
    if(results.value == 4294967295)
      {Serial.print(DU, HEX);}
    dump(&results);
    irrecv.resume(); // Receive the next value
  }
  
 if(Serial.available() > 37)
   {Serial.flush(); }
 if(Serial.available() == 37)
   {
    for(int i=0; i < 37; i++) 
       {inserial[i] = Serial.read() - 48; 
    } 
    Serial.flush();
    }

if(inserial[0]==1 && inserial[1]==1 && inserial[2]==1 && inserial[3]==1)
  {for(int b=0; b < 16; b++) 
      {
       val[b] = map(( inserial[((b*2)+4)] * 10 + inserial[((b*2)+5)]), 0, 63, 0, 255);
      //if(b==5&&inserialAP==1){inserialAP=0;}
      }
   }    
if(val[0]>lastpos[0]&&inserial[36]==1)
  {lastpos[0]++; analogWrite(ledPin3, lastpos[0]);  delay(delayled); }
if(val[1]>lastpos[1]&&inserial[36]==1)
  {lastpos[1]++; analogWrite(ledPin5, lastpos[1]);  delay(delayled); }
if(val[2]>lastpos[2]&&inserial[36]==1)
  {lastpos[2]++; analogWrite(ledPin6, lastpos[2]);  delay(delayled); }
if(val[3]>lastpos[3]&&inserial[36]==1)
  {lastpos[3]++; analogWrite(ledPin9, lastpos[3]);  delay(delayled); }

if(val[0]<lastpos[0]&&inserial[36]==1)
  {lastpos[0]--; analogWrite(ledPin3, lastpos[0]);  delay(delayled); }
if(val[1]<lastpos[1]&&inserial[36]==1)
  {lastpos[1]--; analogWrite(ledPin5, lastpos[1]);  delay(delayled); }
if(val[2]<lastpos[2]&&inserial[36]==1)
  {lastpos[2]--; analogWrite(ledPin6, lastpos[2]);  delay(delayled); }
if(val[3]<lastpos[3]&&inserial[36]==1)
  {lastpos[3]--; analogWrite(ledPin9, lastpos[3]);  delay(delayled); }
if(val[0]==lastpos[0]&&val[1]==lastpos[1]&&val[2]==lastpos[2]&&val[3]==lastpos[3])
  {inserial[36]=0;}
} 

Это от Наны

А вот эти огрызоки в Меге

 if(Serial3.available() > 8) // если с СОМ пришло больше 10 символов стираем буфер
   {Serial3.flush(); }
 if(Serial3.available() == 8)// если буфер СОМ = 10 то пишем в массив
   {DU = "";//inserialAP = 1;
    for(int i=0; i < 8; i++) 
       {inserial[i] = Serial3.read(); 
        DU +=(char)inserial[i];        
        } 
    Serial3.flush();Serial.println(DU);
    }

и 

if(screen == 0)
  {sum_Led = LedOut[0]+LedOut[1]+LedOut[2]+LedOut[3]+LedOut[4]+LedOut[5]+LedOut[6]+LedOut[7]+LedOut[8]+LedOut[9]+LedOut[10]+LedOut[11]+LedOut[12]+LedOut[13]+LedOut[14]+LedOut[15];
     
   if((digitalRead(MenuAP) == HIGH || (DU == "40BF00FF" && millis()-ButTimeTmp>ButTime)) && sum_Led == 0 && LedOn == 0){
      LedOut[0]=start_led;LedOut[1]=start_led;LedOut[2]=start_led;LedOut[3]=start_led;
      LedOut[4]=start_led;LedOut[5]=start_led;LedOut[6]=start_led;LedOut[7]=start_led;
      LedOut[8]=start_led;LedOut[9]=start_led;LedOut[10]=start_led;LedOut[11]=start_led;
      LedOut[12]=start_led;LedOut[13]=start_led;LedOut[14]=start_led;LedOut[15]=start_led;
      Serial3.print(1111);
      for(byte i=0; i<16; i++)
         {if(LedOut[i]/4<10){Serial3.print(0);} Serial3.print(LedOut[i]/4);}
      Serial3.print(1);
      Serial.print(1111);
       for(byte i=0; i<16; i++)
          {if(LedOut[i]/4<10){Serial.print(0);} Serial.print(LedOut[i]/4);}
       Serial.println(1);   
      LedOn = 1;ButTimeTmp = millis();}
   //Длительное нажатие    
   if(digitalRead(MenuAP) == HIGH && sum_Led >0 && LedOn == 0)
     {LedOff=millis(); LedOn = 2;}
   if(digitalRead(MenuAP) == LOW && LedOn > 0){LedOn = 0;LedOftemp = 0;}
   if(((digitalRead(MenuAP)==HIGH&&millis()-LedOff>LedTOff&&LedOn==2)||(DU=="40BF00FF"&&millis()-ButTimeTmp>ButTime))&&sum_Led >0)
     {LedOut[0]=0;LedOut[1]=0;LedOut[2]=0;LedOut[3]=0;LedOut[4]=0;LedOut[5]=0;LedOut[6]=0;LedOut[7]=0;
      LedOut[8]=0;LedOut[9]=0;LedOut[10]=0;LedOut[11]=0;LedOut[12]=0;LedOut[13]=0;LedOut[14]=0;LedOut[15]=0;
      Serial3.print("1111000000000000000000000000000000001");
      analogWrite(ledPin7,LedOut[7]); 
      analogWrite(ledPin13,LedOut[13]);
      ButTimeTmp = millis();
      DesPLMNs = 0;}

Да и я знаю что можно сократить код с помощью for(int i; i<16, i++) и т.д., просто оставил для наглядности, а то местами возвращать приходилось...

Все от меги заливать смысла нет, т.к. только добрался до обмена данными.

Jacks_d
Offline
Зарегистрирован: 31.12.2011

Попробывал допаять к RX/TX последовательно по 1кОм, не помогло, нана вообще перестала видеть приходящие от меги данные, мега нормально.

maksim
Offline
Зарегистрирован: 12.02.2012

Отредактируйте сообщение выше и выложите весь код, потому как если уверены, что там не может быть ошибок связаных с вашей проблемой, то и смысла вообще заводить эту тему тогда нету.

maksim
Offline
Зарегистрирован: 12.02.2012

Первое что хотелось узнать - какой версией Arduino IDE пользуетесь?

Jacks_d
Offline
Зарегистрирован: 31.12.2011

Дык я и написал в аппаратные вопросы, т.к. с софтом уверен, да и на туже граблю наступил когда только начал изучать Arduino, но тогда забил... на мегу заливаю через Arduino IDE 1.0.1, на Нану Arduino IDE 1.0, т.к. только в ней компилируется IRremote.h критичности в этом нет да и удобнее, не нужно каждый раз выбирать нужную плату + два монитора, можно внешним но неудобно

maksim
Offline
Зарегистрирован: 12.02.2012

Что ж если вы так уверены, то хочу вас обрадывать - в Arduino IDE 1.0 не работает Serial.flush(); , не исключено что и в более поздних версиях тоже.

Jacks_d
Offline
Зарегистрирован: 31.12.2011

хммм, поиграюсь с ненормально работой Serial подумаю. дык, а что тогда делать?

Попробую SoftwareSerial.h, но это совтовое( 

maksim
Offline
Зарегистрирован: 12.02.2012

Замените все Serial.flush(); на это

while(Serial.available()) Serial.read();

и еще раз повторяю выложите весь код.

Jacks_d
Offline
Зарегистрирован: 31.12.2011

Смысла нету, я выложил код где встричается Serial, больше его нигде нет. да ипробывал наскетчах из примеров, т.е. там вообще ничего нет, слал тупо значения с аналогового пина и кнопкой поклацывал...

а за 

while(Serial.available()) Serial.read();

спвсибо, я так понимаю, что оно просто читает в воздух и сбрасывает буфер

Jacks_d
Offline
Зарегистрирован: 31.12.2011

кстати, на сколько понимаю SoftwareSerial.h не просто так использует 2 и 3 пин, т.е. там используются прервания, или прерывания самому нужно прописывать?

maksim
Offline
Зарегистрирован: 12.02.2012

Вы уверенны что нигде не вышли за пределы массива?, вы уверенны что не присвоили переменной значенте, которое она не может принять?, да и еще куча всего может быть...

Ну если нет смысла, то и смысла помогать тоже нету. Не вам в обиду, а в пример ваших действий:

Jacks_d
Offline
Зарегистрирован: 31.12.2011

я конечно все понимаю, но врятли вы будите разбирать 2к1 строк кода очень плотного, даже если учесмть что 25% можно выпилить с помощью for(int i; i<16, i++) то разбираться в этом вы врятли будите! А во вторых Спасибо вам за помощь,   

while(Serial.available()) Serial.read();  

таки помогло, про глюки Serial.flush(); не знал, на него и надеялся! т.к. пульт иногда гадит в сиреал почемуто 0ми в место кода, но они отрабатываются Serial.flush(); пока не залипнет... С масивами я точно не выхожу за пределы, уже наиргался и вернулся к одномерным, их проще читать в масив с SD карты. А в бараны лучше так быстро людей не записывайте! Arduino платформа в принцепе не для особо шарющих людей

Кстати не подскажите максимальную длинну на которую может передать UART, для RS232 написано 15м, хотя люди говорили о 50м, но скорость не знаю, на метров 10 его хватит?

maksim
Offline
Зарегистрирован: 12.02.2012

Jacks_d пишет:
А в бараны лучше так быстро людей не записывайте!

Кстати не подскажите максимальную длинну на которую может передать UART, для RS232 написано 15м, хотя люди говорили о 50м, но скорость не знаю, на метров 10 его хватит?

Я в бараны никого не записывал, если вы так считаете, дело ваше.
Вот есть тема про длинну линии дынных.

maksim
Offline
Зарегистрирован: 12.02.2012

Jacks_d пишет:

Arduino платформа в принцепе не для особо шарющих людей

Именно поэтому вас и просят показать весь код, а не куски, в которых вы "уверенны".

Jacks_d
Offline
Зарегистрирован: 31.12.2011

maksim пишет:

Я в бараны никого не записывал, если вы так считаете, дело ваше.

Это я к тому, что дали решение и тут же записали в упертые бараны, хотя я неуспел проверить вашу помощь, если б не помогло то выложил бы, хотя те огрызки что выложил в начале единственные места связаные с сиреалом в чем я обсолютно уверен, т.к. только начал прорабатывать эвзаимодействие о чем и говорил до этого.