随机一段时间后Arduino连接失败循环

时间:2018-11-10 09:32:15

标签: c arduino

我最近开始使用arduino并在 C 中进行编码,偶然发现了一个问题。

一切正常,应该工作:

  

读取NFC标签>将POST发送到Laravel API>接收对以下内容的正文响应   在液晶显示器上显示

但是该程序非常不一致,这意味着在一段未知的时间(这是一个随机的时间段)之后,该程序会返回连接失败,如显示器返回

连接失败后,程序将不会返回到其连接,并且将继续返回连接失败,直到您重新启动程序。

经过数小时的搜索后,我本人无法解决此问题,因此,我要求你们提供帮助。

(不要给我简单的代码作为答案,而是在我正在学习并且想从中学习的同时给我解释。)

硬件:

Arduino MKR1000

Adafruit PN532 NFC / RFID控制器屏蔽(SPI)

监视器返回:

Found chip PN532
Firmware ver. 1.6
Waiting for an ISO14443A card/n
Attempting to connect to SSID: ****
Connected to wifi
SSID: ****
IP Address: ****
signal strength (RSSI):-66 dBm

Starting connection to server...

================= START PROGRAM =======================

Found a card!
UID Length: 4 bytes
UID Value HEX: 67D667E
UID Value Decimal: 6125102126
{"Druppel": "6125102126"}
Connected!
Response:
Tom 
Welcome

Succesfull sign in

Found a card!
UID Length: 4 bytes
UID Value HEX: C9DDCA35
UID Value Decimal: 20122120253
{"Druppel": "20122120253"}
Connection failed

代码

#include <SPI.h>
#include <WiFi101.h>
#include <Wire.h>
#include <LiquidCrystal.h> 
#include <ArduinoJson.h>
#include <Adafruit_PN532.h>

#define PN532_SCK   (9)
#define PN532_MOSI  (8)
#define PN532_SS    (6)
#define PN532_MISO  (10)
#define PN532_IRQ   (2)
#define PN532_RESET (7)
#define TIMEOUT     500

  Adafruit_PN532 nfc(PN532_SCK, PN532_MISO, PN532_MOSI, PN532_SS);  

    const int rs = 12, en = 11, d4 = 2, d5 = 3, d6 = 4, d7 = 5;  
    LiquidCrystal lcd(rs, en, d4, d5, d6, d7);   

    const int ledPin =  1; 
    const int errorLedPin =  13;         
    const int buzzerPin =  0;
    int sensorPin = 0;

    char SSID_NAME[] = "****";        
    char SSID_PASS[] = "****";  

    WiFiClient client;
    int status = WL_IDLE_STATUS;
    int keyIndex = 0;

    char SERVER[] = "****.*****.nl";
    char TOKEN[] = "******************"; 
    char API[] = "********";

void printWiFiStatus() {
  Serial.print("SSID: "); 
  Serial.println(WiFi.SSID());

  Serial.print("IP Address: ");
  Serial.println(WiFi.localIP());

  long rssi = WiFi.RSSI();
  Serial.print("signal strength (RSSI):");
  Serial.print(rssi);
  Serial.println(" dBm");

  lcd.setCursor(0, 0);
  lcd.print("SSID: ");
  lcd.print(WiFi.SSID());

  lcd.setCursor(0, 2);
  lcd.print("IP: ");
  lcd.print(WiFi.localIP());
}


void setup() {
    Serial.begin(9600);

    Serial.println("Serial ready");

    analogWrite(A3, 0);                              
    lcd.begin(16, 2); 

    pinMode(ledPin, OUTPUT);
    pinMode(errorLedPin, OUTPUT);
    pinMode(buzzerPin, OUTPUT);

    tone(buzzerPin, 60);

    nfc.begin();

    uint32_t versiondata = nfc.getFirmwareVersion();
    if (! versiondata) {
      Serial.print("Didn't find PN53x board");
      while (1);                                     
    }

    Serial.print("Found chip PN5");Serial.println((versiondata>>24) & 0xFF, HEX);                
    Serial.print("Firmware ver. ");Serial.print((versiondata>>16) & 0xFF, DEC);Serial.print('.'); Serial.println((versiondata>>8) & 0xFF, DEC); 



    nfc.setPassiveActivationRetries(0xFF);

    nfc.SAMConfig();                                

    Serial.print("Waiting for an ISO14443A card"); Serial.println("/n");


    if (WiFi.status() == WL_NO_SHIELD) {            
      Serial.println("WiFi shield not present");
      while (true);                                 
    }
    noTone(buzzerPin);



    tone(buzzerPin, 50);

    while (status != WL_CONNECTED) {
      Serial.print("Attempting to connect to SSID: ");
      Serial.println(SSID_NAME);

      status = WiFi.begin(SSID_NAME, SSID_PASS);

      delay(100);
    }
    Serial.println("Connected to wifi");
    printWiFiStatus();


    Serial.println("\nStarting connection to server...");
    Serial.println("\n================= START PROGRAM =======================");

    noTone(buzzerPin);
}

void loop() {
  digitalWrite(errorLedPin, LOW);

  boolean success;
  uint8_t uid[] = { 0, 0, 0, 0, 0, 0, 0 };  
  uint8_t uidLength;

  success = nfc.readPassiveTargetID(PN532_MIFARE_ISO14443A, &uid[0], &uidLength);
  if (success) {
    lcd.clear();


      Serial.println("");
      Serial.print("Found a card!");
      Serial.println("");
      Serial.print("UID Length: ");Serial.print(uidLength, DEC);Serial.println(" bytes");
      Serial.print("UID Value HEX: ");

      String data;
      for (uint8_t i=0; i < uidLength; i++) 
      {
        Serial.print(uid[i], HEX); 
        data =  String(data + uid[i]);
      }
      Serial.println("");
      Serial.print("UID Value Decimal: ");
      Serial.print(data); 
      Serial.println("");

      lcd.print(data);

    delay(100);

    digitalWrite(ledPin, HIGH);  

    tone(buzzerPin, 50);
    String PostData = "{\"Druppel\": \"";
    PostData = String(PostData + data);
    PostData = String(PostData + "\"}");
    int PostDataLength = PostData.length() + 1;
    delay(100);
    noTone(buzzerPin);

    char char_array[PostDataLength];

    PostData.toCharArray(char_array, PostDataLength);

    Serial.println(PostData);

    delay(500);
    if(!client.connect(SERVER, 80)) {   
      Serial.println(F("Connection failed"));
      digitalWrite(errorLedPin, HIGH);
      return;
    }

    Serial.println(F("Connected!"));
      client.println("POST /api/******?api_token=****************** HTTP/1.1");
      client.println("Host: ****.*****.nl"); 
      client.println("Cache-Control: no-cache");
      client.println("Content-Type: application/json");
      client.print("Content-Length: ");
      client.println(PostDataLength);
      client.println();
      client.println(PostData);

    client.println(F("Connection: close"));


    if (client.println() == 0) {
      Serial.println(F("Failed to send request"));  
      return;
    }

    char status[32] = {0};
    client.readBytesUntil('\r', status, sizeof(status));
    if (strcmp(status, "HTTP/1.1 200 OK") != 0) {
      Serial.print(F("Unexpected response: "));
      Serial.println(status);
      return;
    }

    char endOfHeaders[] = "\r\n\r\n";
    if (!client.find(endOfHeaders)) {
      Serial.println(F("Invalid response"));
      return;
    }

    const size_t capacity = JSON_OBJECT_SIZE(3) + JSON_ARRAY_SIZE(2) + 60;
    DynamicJsonBuffer jsonBuffer(capacity);

    JsonObject& root = jsonBuffer.parseObject(client);
    if (!root.success()) {
      Serial.println(F("Parsing failed!"));
      return;
    }

    Serial.println(F("Response:"));
    Serial.println(root["User"].as<char*>());
    Serial.println(root["Status"].as<char*>());

    lcd.setCursor(0, 2);
    lcd.print(root["User"].as<char*>());
    lcd.setCursor(0, 0);
    lcd.print(root["Status"].as<char*>());

    client.stop();

    digitalWrite(ledPin, LOW);   

    digitalWrite(errorLedPin, HIGH);
    Serial.println("");
    Serial.println("Succesfull sign in");

    delay(3000);
    lcd.clear();
  } else
  {
    Serial.println("Timed out waiting for a card");
  }
}

1 个答案:

答案 0 :(得分:2)

不要使用String类。它会使内存堆碎片化,从而导致崩溃。使用C字符串(零终止的char数组)。如果您不熟悉strcatsprintf函数,则可以使用我的StreamLib库中的CStringBuilder。该库可在Arduino IDE的库管理器中找到。

char PostData[200];
CStringBuilder sb(PostData, sizeof(PostData));

sb.print("{\"Druppel\": \"");
for (uint8_t i=0; i < uidLength; i++)
{
  sb.print(uid[i]);
  //sb.printf("%02x", uid[i]); // for hex aligned with 0
}
sb.print("\"}");

Serial.println(sb.length());
Serial.println(PostData);