使用延迟时,Arduino SoftSerial不会收到全文

时间:2017-03-19 22:58:59

标签: arduino

我的代码下面有这个奇怪的问题。如果我删除"延迟"行,代码工作正常。如果我将它留在那里,然后通过SoftSerial发送文本,那么该文本将不会作为一个整体收到,但收到的文本将是几个字符短。如果我使用millis进行延迟,也会发生同样的情况。 SoftSerial和延迟是不兼容的吗?有解决方法吗?

#include <SoftwareSerial.h>

#define DEBUG            true
#define relayPin1           8    //Output for relay pin 1
#define relayPin2           7    //Output for relay pin 2
#define relay1Run           5    //Load relay 1 feedback pin 
#define relay2Run           6    //Load relay 2 feedback pin 
#define NOP __asm__ __volatile__ ("nop\n\t")

SoftwareSerial SIM900(10, 11); // RX, TX

char phoneNumber[16]={'\0'};
char simExpirationDate[11]={'\0'};  //31/12/2017
char smsExpirationDate[11]={'\0'};  //31/12/2017
char signalStrength[8]={'\0'};      //100/100
char cardRemainingBalance[7]={'\0'};
char cardExpirationDate[11]={'\0'};  //31-12-2017
char autoReportsOnOff[5]={' ', 'O', 'F', 'F', '\0'};        //AUTO
char outputPinToRelay1[4]={'O', 'F', 'F', '\0'};            //OFF
char outputPinToRelay2[4]={'O', 'F', 'F', '\0'};            //OFF
char relay1State[4]={'O', 'F', 'F', '\0'};                  //OFF
char relay2State[4]={'O', 'F', 'F', '\0'};                  //OFF
byte reportsOnOffSetting = 2;  //0=off, 1=on, 2=auto
int timeout=2000L;
byte tempValue=0;

void setup() {
  // if(DEBUG)Serial.begin(9600);
  Serial.begin(9600);
  SIM900.begin(9600);
  pinMode(relayPin1, OUTPUT);
  digitalWrite(relayPin1, HIGH);
  pinMode(relayPin2, OUTPUT);
  digitalWrite(relayPin2, HIGH);
  pinMode(relay1Run, INPUT);
  digitalWrite(relay1Run, HIGH);
  pinMode(relay2Run, INPUT);
  digitalWrite(relay2Run, HIGH);
}

void loop() {
  char *textReceived;
  textReceived = (char *) malloc(90);
  if(SIM900.available()) {
    delay(1000);
    readData(timeout, 89, textReceived);
    Serial.print("textReceived: ");
    Serial.println(textReceived);
    free(textReceived);
    delay(40000L);
  }
}

byte readData(long int timeout,int charsToRead, char *textRecieved) {
  unsigned long time = millis();
  byte counter=0;
  while((time+3000L) > millis()) {
    while(SIM900.available()) {
      if(counter>=charsToRead)SIM900.read();
      else {
        textReceived[counter] = SIM900.read();
        if((textReceived[counter]) == '\0')goto here;
        counter++;
      }
    }
  }
  textReceived[counter] = '\0';
  return counter;
  here:
    return counter;
}

void sendData(char *data) {
  SIM900.print(data); // send the read character to the ESP8266
  if(DEBUG) Serial.println(data);
 }

2 个答案:

答案 0 :(得分:0)

您的缓冲区可能正在超支。此外,您的代码有2个延迟。也许你可以说你在谈论哪一行。

最后,您正在使用池方法来读取UART。您应尽可能尝试使用中断。你可以在这里找到一些好的信息:https://www.arduino.cc/en/Tutorial/SerialEvent

答案 1 :(得分:0)

首先,我不会写这样的代码。但要解决您的问题,您应该在while(SIM900.available())循环中稍微延迟。 问题是循环运行的速度比串行数据的速度快,因此即使有更多数据出现,SIM900.available()语句也将为false。 delay(1);可以正常使用。

喜欢这个。

while(SIM900.available()) {
  if(counter>=charsToRead)SIM900.read();
  else {
    textReceived[counter] = SIM900.read();
    if((textReceived[counter]) == '\0')goto here;
    counter++;
  }
  delay(1);  // Add this.
}